当前位置: 首页 > 知识库问答 >
问题:

空JTabbedPane

华季萌
2023-03-14

我在创建一个空的JTabbedPane时遇到了一个问题,在该JTabbedPane中,在GUI上可以看到的唯一部分是那一行选项卡。

当前的解决办法是重写getPreferredSize(),但在我看来这似乎很笨拙。注释掉重写的方法,看看我的意思。

我是不是漏掉了什么明显的东西?

背景:

import java.awt.*;
import java.awt.event.*;

import javax.swing.*;

public class CustomTabbedPane implements Runnable
{
  static final int MAX_TABS = 11; // includes the "add" tab

  JPanel pnlTabs;
  JTabbedPane tabbedPane;

  public static void main(String[] args)
  {
    SwingUtilities.invokeLater(new CustomTabbedPane());
  }

  public void run()
  {
    JPanel p = buildPanel();
    JFrame frame = new JFrame();
    frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    frame.setContentPane(p);
    frame.setSize(800,400);
    frame.setVisible(true);
  }

  private JPanel buildPanel()
  {
    tabbedPane = new JTabbedPane()
    {
      @Override
      public Dimension getPreferredSize()
      {
        Dimension dim = super.getPreferredSize();
        dim.height = getUI().getTabBounds(this, 0).height + 1;
        return dim;
      }
    };

    tabbedPane.addTab("Tab 1", getEmptyComp());
    tabbedPane.addTab("Tab 2", getEmptyComp());
    tabbedPane.addTab("+", new TabCreator());

    tabbedPane.addMouseListener(new MouseAdapter()
    {
      @Override
      public void mouseClicked(MouseEvent e)
      {
        addTab();
      }
    });

    JScrollPane scroll = new JScrollPane(new JTable(5,10));

    JPanel p = new JPanel(new BorderLayout());
    p.add(tabbedPane, BorderLayout.NORTH);
    p.add(scroll,  BorderLayout.CENTER);
    p.setBorder(BorderFactory.createLineBorder(Color.BLUE.darker(), 1));

    return p;
  }

  private void addTab()
  {
    if (tabbedPane.getSelectedComponent() instanceof TabCreator)
    {
      int selIndex = tabbedPane.getSelectedIndex();

      if (tabbedPane.getComponentCount() < MAX_TABS)
      {
        if (selIndex == tabbedPane.getComponentCount()-1)
        {
          String title = "Tab " + (selIndex + 1);
          tabbedPane.insertTab(title, null, getEmptyComp(), "", selIndex);
          tabbedPane.setSelectedIndex(selIndex);

          if (tabbedPane.getComponentCount() == MAX_TABS)
          {
            tabbedPane.setEnabledAt(MAX_TABS-1, false);
          }
        }
      }
    }
  }

  private Component getEmptyComp()
  {
    return Box.createVerticalStrut(1);
  }

  class TabCreator extends JLabel {}
}

共有1个答案

拓拔元徽
2023-03-14

好问题!但是想要了解正在发生的事情是相当简单的。

问题是您的内容没有最小宽度,没有设置首选大小,选项卡的位置是顶部/底部,并且UI是默认的。

由于未设置首选大小,因此当重新验证布局时,所需空间的计算进入BasicTabbedPaneui方法Dimension calculateSize(false)

int height = 0;
int width = 0;
<other vars>
// Determine minimum size required to display largest
// child in each dimension
<actual method>

在这里,它计算容纳任何子级的最小大小,并将其存储到height/width中。在您的例子中,这会产生类似于10,10的结果(因为单标签选项卡的创建者,我想,我没有遵循这一条)。

然后神奇的事情发生了:

switch(tabPlacement) {
    case LEFT:
    case RIGHT:
        height = Math.max(height, calculateMaxTabHeight(tabPlacement));
        tabExtent = preferredTabAreaWidth(tabPlacement, height - tabAreaInsets.top - tabAreaInsets.bottom);
        width += tabExtent;
        break;
    case TOP:
    case BOTTOM:
    default:
        width = Math.max(width, calculateMaxTabWidth(tabPlacement));
        tabExtent = preferredTabAreaHeight(tabPlacement, width - tabAreaInsets.left - tabAreaInsets.right);
        height += tabExtent;
}

这里发生的是,它将首选宽度设置为最大选项卡宽度和最大子宽度中的最大值。在您的例子中,标签文本大约是44。然后计算tabextent以查看支持此首选宽度需要多少行制表符。在您的情况下-它是为每个选项卡额外的1行选项卡。这就是preferredSize().height中额外高度的来源。本质上是因为对于水平选项卡放置,它首先关心宽度,然后是高度。

    null

编辑:

在对此进行了更多的思考之后,我意识到解决方案1和您自己的解决方案存在这样一个缺陷:如果选项卡窗格确实需要多行选项卡(hello帧大小),那么就会发生坏的事情。别用了。

 类似资料:
  • 问题内容: 从目前的情况来看,这个问题不适合我们的问答形式。我们希望答案会得到事实,参考或专业知识的支持,但是这个问题可能会引起辩论,争论,民意测验或进一步的讨论。如果您认为此问题可以解决并且可以重新提出,请访问帮助中心以获取指导。 8年前关闭。 在sql数据库列中,除非我们使用指定,否则将将空字段设置为。用一种代替另一种的优点是什么?谢谢! 问题答案: 如果需要在列中表示未知数据,请使其为可为空

  • 本文向大家介绍sitecore 空/空检查,包括了sitecore 空/空检查的使用技巧和注意事项,需要的朋友参考一下 示例 IsNotNull 这是一种非常简单且流行的方法,用于检查项目是否不为空。它只是检查传入的对象是否为空。 IsNotNullOrEmpty 这与上面的IsNotNull相同,但是适用于字符串值而不是对象。 一片空白 这只是该IsNotNull()方法的逆过程。此方法断言该对

  • 我是XML验证方面的新手,在调用adobe server生成PDF之前,我被要求对XML进行验证。我有以下内容,我们通过对象获取XML,然后调用。如果有任何元素为null或空以停止生成pdf,任何人都可以帮助我一步一步地验证XML吗

  • 文件系统负责将空闲块分配给文件,因此它必须跟踪磁盘中存在的所有空闲块。 主要有两种方法,使用它们管理磁盘中的空闲块。 1. 位向量 在这种方法中,空闲空间列表被实现为位图向量。 它包含每个位代表每个块的位数。 如果该块为空,则该位为1,否则为0。最初,所有块都是空的,因此位图向量中的每个位都包含1。 随着空间分配的进行,文件系统开始为文件分配块并将各个位设置为。 2. 链接列表 这是空闲空间管理的

  • 问题内容: 在Java代码中执行空检查时,如果您为空值抛出IllegalArgumentExceptions,那么您将使用哪种消息模板? 我们倾向于使用这样的东西 哪个更好:“ is null”或“ was null”,为什么? 对我来说,“是空的”感觉更自然。 问题答案: 由于由于失败的前提条件检查而引发,因此,我认为除了陈述事实以外,还应说明已违反的 要求 。 就是说,而不是说。 关于使用库进

  • 问题内容: 我想获取字段的字符串值(它们可以是长字符串或任何对象的类型), 如果一个字段为空,那么它应该返回空字符串,我用番石榴做过; 但是如果gearbox为null,则返回null!非空字符串,因为valueOf methdod返回字符串“ null”,这会导致错误。 有任何想法吗? EDIt:有100多个字段,我正在寻找易于实现的字段 问题答案: 您可以使用(Java 7中的标准): 从链接