3

I want to put some effects on my program buttons. When I press the button,the button should fade in.

Using a timer to change the value of Opaque in new Color() is one of the way, but can it applied to JButton as well? Because the JButton has border.

So, I want to ask that is it possible to create a fade in effect for JButton using a Timer?

If yes, can I ask for an example?

Chin
  • 593
  • 4
  • 15
  • 36

2 Answers2

9

Is it possible to create a fade in effect for JButton using Timer?

I think that no issue with that,

If yes, can I ask for an example?

why not

import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.Color;
import java.awt.AlphaComposite;
import javax.swing.*;
import javax.swing.UIManager.LookAndFeelInfo;

public class ButtonTest {

    private JFrame frame;
    private JButton opaqueButton1;
    private JButton opaqueButton2;
    private SoftJButton softButton1;
    private SoftJButton softButton2;
    private Timer alphaChanger;

    public void createAndShowGUI() {
        opaqueButton1 = new JButton("Opaque Button");
        opaqueButton2 = new JButton("Opaque Button");
        softButton1 = new SoftJButton("Transparent Button");
        softButton2 = new SoftJButton("Transparent Button");
        opaqueButton1.setBackground(Color.GREEN);
        softButton1.setBackground(Color.GREEN);
        frame = new JFrame();
        frame.getContentPane().setLayout(new java.awt.GridLayout(2, 2, 10, 10));
        frame.add(opaqueButton1);
        frame.add(softButton1);
        frame.add(opaqueButton2);
        frame.add(softButton2);
        frame.setSize(700, 300);
        frame.setLocation(150, 100);
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.setVisible(true);
        alphaChanger = new Timer(30, new ActionListener() {

            private float incrementer = -.03f;

            @Override
            public void actionPerformed(ActionEvent e) {
                float newAlpha = softButton1.getAlpha() + incrementer;
                if (newAlpha < 0) {
                    newAlpha = 0;
                    incrementer = -incrementer;
                } else if (newAlpha > 1f) {
                    newAlpha = 1f;
                    incrementer = -incrementer;
                }
                softButton1.setAlpha(newAlpha);
                softButton2.setAlpha(newAlpha);
            }
        });
        alphaChanger.start();
        Timer uiChanger = new Timer(3500, new ActionListener() {

            private final LookAndFeelInfo[] laf = UIManager.getInstalledLookAndFeels();
            private int index = 1;

            @Override
            public void actionPerformed(ActionEvent e) {
                try {
                    UIManager.setLookAndFeel(laf[index].getClassName());
                    SwingUtilities.updateComponentTreeUI(frame);
                    opaqueButton1.setText(laf[index].getClassName());
                    softButton1.setText(laf[index].getClassName());
                } catch (Exception exc) {
                    exc.printStackTrace();
                }
                index = (index + 1) % laf.length;
            }
        });
        uiChanger.start();
    }

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

            @Override
            public void run() {
                new ButtonTest().createAndShowGUI();
            }
        });
    }

    private static class SoftJButton extends JButton {

        private static final JButton lafDeterminer = new JButton();
        private static final long serialVersionUID = 1L;
        private boolean rectangularLAF;
        private float alpha = 1f;

        SoftJButton() {
            this(null, null);
        }

        SoftJButton(String text) {
            this(text, null);
        }

        SoftJButton(String text, Icon icon) {
            super(text, icon);
            setOpaque(false);
            setFocusPainted(false);
        }

        public float getAlpha() {
            return alpha;
        }

        public void setAlpha(float alpha) {
            this.alpha = alpha;
            repaint();
        }

        @Override
        public void paintComponent(java.awt.Graphics g) {
            java.awt.Graphics2D g2 = (java.awt.Graphics2D) g;
            g2.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER, alpha));
            if (rectangularLAF && isBackgroundSet()) {
                Color c = getBackground();
                g2.setColor(c);
                g.fillRect(0, 0, getWidth(), getHeight());
            }
            super.paintComponent(g2);
        }

        @Override
        public void updateUI() {
            super.updateUI();
            lafDeterminer.updateUI();
            rectangularLAF = lafDeterminer.isOpaque();
        }
    }
}
mKorbel
  • 109,525
  • 20
  • 134
  • 319
  • Your code seems to be too complicated to my level... @_@ But I'll try it. Thanks for the reply. – Chin May 21 '12 at 11:09
  • @AnonyNewbie: Compare this related [example](http://stackoverflow.com/a/2234020/230513). – trashgod May 21 '12 at 14:29
2

Yes, this should be possible. You can specify a colour in terms of RGBA, where A is alpha (or opacity), and then apply this colour (or separate colours with the same alpha value, if you wish) to the border, the background and the foreground or the JButton.

button.setForeground( *colour* );
button.setBackground( *colour* );
button.setBorder( BorderFactory.createBevelBorder( BevelBorder.RAISED, *highlight colour*, *shadow colour* ) );
Jamie
  • 3,890
  • 3
  • 26
  • 35
  • I understand the `setForeground()` and `setBackground()`, but I not so understand the `setBorder()` mentioned. What does it means by the `*highlight colour*` and `*shadow colour*`? – Chin May 21 '12 at 11:12
  • We're creating a new beveled border to apply to the button. A beveled border isn't just one colour, but actually two - the highlight colour and the shadow colour. These are used to draw the "beveled" edge of the border. They can be whatever colour you like, just make sure you adjust the alpha value appropriately! – Jamie May 21 '12 at 11:15
  • So, can I use something like `new Color(123, 123, 123, 50)` to replace the `*highlight colour*` and `*shadow colour*`? – Chin May 21 '12 at 12:14
  • Yes, exactly. But you want to reassign these colours inside your timer, incrementing/decrementing the last value (50, in this case) to achieve your "fade" effect – Jamie May 21 '12 at 13:01