0

I have a subclass of JFrame(it contains JButton, Title and Jpanel) and i added a JPanel to it. Jpanel occupies center portion of borderlayout. I want to make JPanel to be transparent(it should see through the Frame window).

As i am doing it for Java 1.5, I used JFrame.setOpacity(0.0f) to set transparency of Jframe. By doing this all Components of JFrame(ie. button, Title ahd jPanel) are using same alpha level. But I want only JPanel to be Transparent.

I experimented with JLayeredPane by changing Z-order with the same result.

I am open to use external libraries like JNA(JNA windowsUtil is also doing the same as setOpacity() method) and using classes of java7 or java6 as external libraries to my application .

I even gone through some previously asked questions with no help:

Opaque components on transparent Java windows

Java: Transparent Windows with non-transparent components?

Re-paint on translucent frame/panel/component.

Community
  • 1
  • 1
E V
  • 43
  • 1
  • 7
  • If you use the JNA utilities, you *may* be able to get the desired effect by setting an alpha mask on the window indicating your desired opacity level, and then put your non-opaque bits into a heavyweight component within the original window. Whether this works largely depends on how transparency cascades down a window hierarchy on the given platform. – technomage May 15 '12 at 11:40
  • BTW, the JNA utilities provide for setting a global window alpha, a window bitmask, and an alpha mask. The last is most likely to work for what you are trying to do. You're not likely to get java[67] code to work with an earlier JVM. – technomage May 15 '12 at 13:02

2 Answers2

1

Use JNA's WindowUtils.setWindowTransparent() method to start with a completely transparent window. Any pixels painted into that window will have their alpha component preserved.

JFrame f = ...
WindowUtils.setWindowTransparent(f, true);
// ensure JPanel content pane doesn't paint its (solid) background
f.getContentPane().setOpaque(false);
// Any other added components will be painted normally
f.getContentPane().add(new JButton("I'm opaque"));

This should deliver the desired results.

If you want your container to be semi-transparent, or other opacity combinations, you'll need to clarify your desired results.

technomage
  • 9,861
  • 2
  • 26
  • 40
  • 1
    Thank you for your time in helping me...But I am afraid that the above one is not working. As you know that JButton is a lightweight object, it takes it's alpha value from it's ancestor's window. – E V May 17 '12 at 04:43
  • I saw a post of yours :http://rabbit-hole.blogspot.in/2007/04/alpha-mask-transparency.html. Can you give me the link of source code of that article. And can you please provide information regarding what masking actually does in JNA – E V May 17 '12 at 04:44
  • 1
    That code is included in the JNA project. Usually, a button's LAF will paint the button's content area and leave its background painting up to its parent. If your button does not paint its content area fully, you will either need to modify it so that it does, or use setOpaque(true) on it (to get the default bg), or give it a parent that paints its background. – technomage May 17 '12 at 13:56
  • 1
    There are three functions in the JNA `WindowUtils`. `setWindowMask` turns pixels on (painted) or off (fully transparent). `setWindowAlpha` applies an alpha value to the entire window (and its contents). `setWindowTransparent` composites all painting to the window with its supplied alpha component. – technomage May 17 '12 at 13:59
0

Here is a small example with two labels. One being fully opaque while the other is semi-transparent. This can work as well with JPanel, but for demonstration-purposes, it is more examplative with JLabel:

import java.awt.BorderLayout;
import java.awt.Color;

import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.SwingUtilities;

import com.sun.awt.AWTUtilities;

public class Test3 {

    protected static void initUI() {
        JFrame frame = new JFrame("test");
        frame.setUndecorated(true);
        AWTUtilities.setWindowOpaque(frame, false);
        JLabel label = new JLabel("Hello NOT transparent label");
        label.setOpaque(true);
        label.setBackground(new Color(255, 0, 0));
        JLabel transLabel = new JLabel("Hello transparent label");
        transLabel.setOpaque(true);
        transLabel.setBackground(new Color(255, 0, 0, 50));
        frame.setLocationByPlatform(true);
        frame.getContentPane().add(label);
        frame.getContentPane().add(transLabel, BorderLayout.SOUTH);
        frame.pack();
        frame.setVisible(true);
    }

    public static void main(String[] args) {
        SwingUtilities.invokeLater(new Runnable() {

            @Override
            public void run() {
                initUI();
            }
        });
    }
}
Guillaume Polet
  • 47,259
  • 4
  • 83
  • 117
  • Thank you for the reply. As i said I wanted to do the application for java1.5 (which don't have AWTUtilities.setWindowOpaque method), so tried to use the class of jre1.6u10 as my dependency librabries, but it has problems with duplication of the classes from jre1.5. So, can u help me if there are any alternatives...... – E V May 14 '12 at 10:28
  • @user1371881 I think then that you are out of luck. See also this post: http://stackoverflow.com/questions/1416869/how-to-distribute-awtutilities – Guillaume Polet May 14 '12 at 10:31
  • I already saw that post...and tried my part to get rid of dependencies by changing the names of the classes, but there are many changes in jre1.6u10 wrt jre1.5. So, I gave up that process and looking for native library alternatives like JNA(which in fact is not helpful). There are some screen Capture WEbsites like www.screencast-o-matic.com, which are doing the samething even with jre1.5. So there got to be some way – E V May 14 '12 at 10:41
  • In what way was JNA not helpful? See http://twall.github.com/jna/3.4.0/javadoc/com/sun/jna/platform/WindowUtils.html. You need to then explicitly paint each component at the desired opacity level (you can do this by subclassing JPanel and overriding its paint methods to paint into a buffer and then draw that buffer to the original graphics context with the desired transparency level). – technomage May 15 '12 at 13:05
  • @technomage i was using a subclass of JPanel as a contentPane of JFrame and in it's paint method i was drawing an fillrect with gradient paint(whose opacity value is1.0).But thing is that the contentPane is taking the opacity level of its parent window.BTW what did you mean by"overriding its paint methods to paint into a buffer and then draw that buffer to the original graphics context with the desired transparency level".I didn't get what to"paint into a buffer".Did you mean to paint components of contentPane?If am wrong,please correct me and help me if i am missing any usage knowledge of JNA – E V May 16 '12 at 13:57
  • @technomag I was using opacity alpha value of 0.5 through WindowUtils of jna to my JFrame. I want the Components(buttons) of contentPane of Jframe to be Opaque. But they are talking the opacity level of jFrame. – E V May 16 '12 at 14:03