【问题标题】:Swing - last JMenuItem occupy the rest of space on JMenuBarSwing - 最后一个 JMenuItem 占据了 JMenuBar 上的剩余空间
【发布时间】:2017-08-01 09:22:01
【问题描述】:

我发现如果我有一个JMenuBar,并且它的最后一个元素(最右边的那个)是一个JMenuItem,它会占据JMenuBar上所有剩余的空白空间,这绝对不是我们想要的.

想象一个“关于”JMenuItem 作为 JMenuBar 上最右边的项目。它应该只占用与其他菜单相同的空间。

查看我的SSCCE:(单击菜单并将鼠标悬停在右侧的菜单项上查看效果)

import java.awt.Dimension;

import javax.swing.JFrame;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JMenuItem;
import javax.swing.SwingUtilities;

public class JMenuItemLastOnMenuBar {

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

            @Override
            public void run() {
                createGUI();
            }
        });
    }

    private static void createGUI() {
        JFrame frame = new JFrame();
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        frame.setBounds(0, 0, 300, 300);

        JMenuBar bar = new JMenuBar();
        JMenu menu = new JMenu("Menu 1");
        JMenuItem item1 = new JMenuItem("Item 1");
        menu.add(item1);
        bar.add(menu);

        JMenuItem item2 = new JMenuItem("Item 2") {
            @Override
            public Dimension getPreferredSize() {
                return new Dimension(120, 25);
            }
        };
        bar.add(item2);

        frame.setJMenuBar(bar);

        frame.pack();
        frame.setVisible(true);
    }

}

【问题讨论】:

  • 为什么代码会覆盖item2的首选大小?
  • 你应该在末尾添加一个分隔符/间隔...
  • @AndrewThompson 因为我想让它始终返回适当的首选大小以供布局管理器使用。或者别的什么。
  • @UsagiMiyamoto 这个想法很有趣,但这行不通。我试过了,剩下的空白被切成两半,JMenuItem占据了前/左半部分。

标签: java swing jmenuitem jmenubar


【解决方案1】:

你应该重写方法getMaximumSize

import java.awt.Dimension;

import javax.swing.JFrame;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JMenuItem;
import javax.swing.SwingUtilities;

public class JMenuItemLastOnMenuBar {

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

            @Override
            public void run() {
                createGUI();
            }
        });
    }

    private static void createGUI() {
        JFrame frame = new JFrame();
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        frame.setBounds(0, 0, 300, 300);

        JMenuBar bar = new JMenuBar();
        JMenu menu = new JMenu("Menu 1");
        JMenuItem item1 = new JMenuItem("Item 1");
        menu.add(item1);
        bar.add(menu);

        JMenuItem item2 = new JMenuItem("Item 2") {
            @Override
            public Dimension getMaximumSize() {
                Dimension d1 = super.getPreferredSize();
                Dimension d2 = super.getMaximumSize();
                d2.width = d1.width;
                return d2;
            }
        };
        bar.add(item2);

        frame.setJMenuBar(bar);

        frame.pack();
        frame.setVisible(true);
    }

}

【讨论】:

  • 这行得通。现在 JMenuItem 更小且可控,谢谢!现在已经无关紧要了,但为什么 JMenuBar 上的 JMenuItem 没有悬停动画?
  • @FaithReaper 它没有在您使用的 L&F 中实现。部分L&F支持悬停动画(试试set the Windows L&F)。
  • @SergiyMendvynskyy 我已经检查过了,但它不起作用。只有在我单击菜单并将鼠标悬停在菜单中的 JMenuItem 上一次后,才会显示悬停动画。如果我关闭菜单,第二个项目没有动画。
  • JMenuItem 通常在单击它们所属的菜单之前不可见。这可能是处理悬停方式的原因......
  • 嗯。我也这么认为。不过很奇怪:在 JMenubar 中有一个 JMenuItem 是很常见的。至少,这是合法的。 Swing 有问题。
猜你喜欢
  • 2019-01-19
  • 1970-01-01
  • 2019-04-22
  • 2011-06-17
  • 2013-02-22
  • 1970-01-01
  • 2021-11-04
  • 2021-11-10
  • 1970-01-01
相关资源
最近更新 更多