JTabbedPane customize tab

I want to customize the look of tabs in JTabbedPane.
I want to start with the simplest and simplest behavior: no borders, solid color.
The problem is that it is still unclear: the tabs are slightly overlapped by the brand.

enter image description here

You see that since the second tab is selected, it is “brought to the fore.” This is achieved by slightly overlapping the field. Is there a (not complicated) way to disable this behavior?

simple, verifiable (fix import only) code:

public class TabbedPane_LookStudy extends JFrame{ public static void main(String [] args) throws UnsupportedLookAndFeelException { UIManager.setLookAndFeel(new NimbusLookAndFeel()); new TabbedPane_LookStudy().setVisible(true); } public TabbedPane_LookStudy() { JTabbedPane tp = new JTabbedPane(); tp.setUI(new MyTabbedPaneUI()); add(tp); tp.addTab("first",new JPanel()); tp.addTab("second", new JPanel()); tp.addTab("third", new JPanel()); setPreferredSize(new Dimension(180,100)); pack(); } public static class MyTabbedPaneUI extends javax.swing.plaf.basic.BasicTabbedPaneUI { @Override protected void paintTab(Graphics g, int tabPlacement, Rectangle[] rects, int tabIndex, Rectangle iconRect, Rectangle textRect) { Color savedColor = g.getColor(); g.setColor(Color.PINK); g.fillRect(rects[tabIndex].x, rects[tabIndex].y, rects[tabIndex].width, rects[tabIndex].height); g.setColor(Color.BLUE); g.drawRect(rects[tabIndex].x, rects[tabIndex].y, rects[tabIndex].width, rects[tabIndex].height); g.setColor(savedColor); } } 

}

+8
java swing jtabbedpane
source share
4 answers

The correct way is to implement only a custom look and feel . But if you want to play with XxxTabbedPaneUI , then perhaps this post can help you with this.

for Nimbus it is better to check aephyr code depot

+4
source share

The first (partial) solution. I found the "positioning" code.
This is the calculateTabRects method in TabbedPaneLayout , an inner class of BasicTabbedPaneUI. The method is extremely complex, but the good part is that the part that “raises the front” of the tab is well commented and isolated by its own overrideable method! This is padSelectedTab .

Create a class that does nothing and does not raise a component as simple as:

  protected class MyTabbedPaneLayout extends TabbedPaneLayout { @Override protected void padSelectedTab(int tabPlacement, int selectedIndex) { //do nothing! //super.padSelectedTab(tabPlacement, selectedIndex); } } 

Note that this must be the inner class MyTabbedPane. It must be created by overriding MyTabbedPane.createLayoutManager:

 @Override protected LayoutManager createLayoutManager() { //return super.createLayoutManager(); return new MyTabbedPaneLayout(); } 

Very simple and actually works ... except in case. CreateLayoutManager creates an instance of TabbedPaneLayout if tabLayoutPolicy is WRAP_TAB_LAYOUT, but creates an instance of TabbedPanelScrollLayout if tabLayoutPolicy is SCROLL_TAB_LAYOUT. The latter has private and unsecured access, so it cannot be a subclass!
My implementation of createLayoutManager loses scrollable behavior.

+2
source share

You can override paintContentBorderTopEdge in MyTabbedPaneUI so that it does not think that any of the tabs is selected. This is not a very acceptable solution, but UI hacker classes rarely adapt to my experience :)

 @Override protected void paintContentBorderTopEdge(Graphics g, int tabPlacement, int selectedIndex, int x, int y, int w, int h) { super.paintContentBorderTopEdge(g, tabPlacement, -1, x, y, w, h); } 
+1
source share

You can put the Html tags in the first parameter as follows:

MyJTabbedPane.addTab("<html><h1 style='padding:20px;'>TEST</h1></html>", new JPanel());

+1
source share

All Articles