Joaco Terniro
Joaco Terniro

Reputation: 115

How to take out white borders in JMenu and JMenuItems

I'm doing this Graphic Interface with Swing. The problem that i'm having is that i can't take the white borders that are arround the JMenuItems, and paint it all of black. Here is an image:

enter image description here

I would like to paint it like this (I have edited the image with paint :D):

enter image description here

Could someone help me? I'll appreciate any help. Thank you!

Upvotes: 3

Views: 2446

Answers (2)

coder
coder

Reputation: 12992

I am adding a second approach. You could use setBorder method:

menuBar.setBorder(BorderFactory.createLineBorder(Color.BLUE, 2));

This solution has the advantage that you can set the level of thickness. In the example above level of thickness is set to 2.

Also you can use setBorder in many components to paint various borders as in the example below:

First the basic code:

Main class:

import javax.swing.*;

public class Main {

    public static void main(String[] args) {

        SwingUtilities.invokeLater(() -> {
            CustomGUI sw = new CustomGUI();
            sw.setVisible(true);
        });

    }
} 

CustomGui.class:

import java.awt.*;
import javax.swing.*;

public class CustomGUI extends JFrame {

    public CustomGUI()  {
        super("Simple example");
        setLayout(new GridBagLayout());
        GridBagConstraints c = new GridBagConstraints();
        setSize(500,500);
        setLocationRelativeTo(null);
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        getContentPane().setBackground(Color.DARK_GRAY);



        JMenuBar menuBar = new JMenuBar();
        JMenu menu1 = new JMenu("menu B");
        menuBar.add(menu1);

        JMenuItem item = new JMenuItem("A text-only menu item");
        menu1.add(item);

        JMenu menu2 = new JMenu("menu B");
        menuBar.add(menu2);

        JMenuItem item2 = new JMenuItem("A text-only menu item");
        menu2.add(item2);


        add(menuBar);
    }
}

Now by adding line:

menuBar.setBorder(BorderFactory.createLineBorder(Color.BLUE, 2));

in CustomGUI() we get: enter image description here

Now if we want to add border to jmenu's (which is what the OP asked) as well add:

menu1.getPopupMenu().setBorder(BorderFactory.createLineBorder(Color.BLUE, 4));
menu2.getPopupMenu().setBorder(BorderFactory.createLineBorder(Color.BLUE, 4));

enter image description here (as you can see in the image i didn't set border for menubar but this could be done as described above using: menuBar.setBorder(BorderFactory.createLineBorder(Color.BLUE, 2)); And also I added another item just for the menu to be bigger and easier to see the border...)

Upvotes: 0

MadProgrammer
MadProgrammer

Reputation: 347332

I just did this quick test, using

UIManager.put("PopupMenu.border", new LineBorder(Color.RED));

Test

import java.awt.Color;
import java.awt.Dimension;
import java.awt.EventQueue;
import java.awt.Graphics;
import java.awt.Graphics2D;
import javax.swing.JFrame;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JMenuItem;
import javax.swing.JPanel;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;
import javax.swing.border.LineBorder;

public class Test {

    public static void main(String[] args) {
        new Test();
    }

    public Test() {
        EventQueue.invokeLater(new Runnable() {
            @Override
            public void run() {
                try {
                    UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
                } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
                    ex.printStackTrace();
                }

                UIManager.put("PopupMenu.border", new LineBorder(Color.RED));

                JMenuBar menuBar = new JMenuBar();
                JMenu menu = new JMenu("Stuff");
                menu.add(new JMenuItem("A"));
                menu.add(new JMenuItem("BB"));
                menu.add(new JMenuItem("CCC"));
                menuBar.add(menu);

                JFrame frame = new JFrame("Testing");
                frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                frame.add(new TestPane());
                frame.setJMenuBar(menuBar);
                frame.pack();
                frame.setLocationRelativeTo(null);
                frame.setVisible(true);
            }
        });
    }

    public class TestPane extends JPanel {

        public TestPane() {
        }

        @Override
        public Dimension getPreferredSize() {
            return new Dimension(200, 200);
        }

    }

}

Now, this may not be desirable, as this will effect ALL popup menus in your program

Updated

I had a look at JMenu and through it's UI delegates and it appears that the popup menu is created within a private method of JMenu called ensurePopupMenuCreated, which would have been an excellent place to inject your custom code.

The method is actually called in a number of different places, but possibly the getPopupMenu is the most accessible

Help

import java.awt.Color;
import java.awt.Dimension;
import java.awt.EventQueue;
import java.awt.event.KeyEvent;
import javax.swing.JFrame;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JMenuItem;
import javax.swing.JPanel;
import javax.swing.JPopupMenu;
import javax.swing.KeyStroke;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;
import javax.swing.border.Border;
import javax.swing.border.LineBorder;

public class Test {

    public static void main(String[] args) {
        new Test();
    }

    public Test() {
        EventQueue.invokeLater(new Runnable() {
            @Override
            public void run() {
                try {
                    UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
                } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
                    ex.printStackTrace();
                }

                JMenuBar menuBar = new JMenuBar();
                JMenu menu = new JMenu("Stuff") {
                    private Border border = new LineBorder(Color.RED);
                    @Override
                    public JPopupMenu getPopupMenu() {
                        JPopupMenu menu = super.getPopupMenu();
                        menu.setBorder(border);
                        return menu;
                    }

                };
                JMenuItem mi = new JMenuItem("Help", 'H');
                mi.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_H, KeyEvent.META_MASK));
                menu.add(new JMenuItem("A"));
                menu.add(new JMenuItem("BB"));
                menu.add(new JMenuItem("CCC"));
                menu.add(mi);
                menuBar.add(menu);

                JFrame frame = new JFrame("Testing");
                frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                frame.add(new TestPane());
                frame.setJMenuBar(menuBar);
                frame.pack();
                frame.setLocationRelativeTo(null);
                frame.setVisible(true);
            }
        });
    }

    public class TestPane extends JPanel {

        public TestPane() {
        }

        @Override
        public Dimension getPreferredSize() {
            return new Dimension(200, 200);
        }

    }

}

Upvotes: 7

Related Questions