Browse Source

Added option to center tabs in JTabbedPane.

pull/127/head
weisj 5 years ago
parent
commit
e69ea7d525
  1. 3
      core/src/main/java/com/github/weisj/darklaf/ui/tabbedpane/DarkHandler.java
  2. 18
      core/src/main/java/com/github/weisj/darklaf/ui/tabbedpane/DarkTabbedPaneLayout.java
  3. 27
      core/src/main/java/com/github/weisj/darklaf/ui/tabbedpane/DarkTabbedPaneScrollLayout.java
  4. 6
      core/src/main/java/com/github/weisj/darklaf/ui/tabbedpane/DarkTabbedPaneUI.java
  5. 5
      core/src/main/java/com/github/weisj/darklaf/ui/tabbedpane/TabbedPaneLayout.java
  6. 101
      core/src/main/java/com/github/weisj/darklaf/ui/tabbedpane/TabbedPaneScrollLayout.java

3
core/src/main/java/com/github/weisj/darklaf/ui/tabbedpane/DarkHandler.java

@ -154,6 +154,9 @@ public class DarkHandler extends TabbedPaneHandler {
ui.westComp = null; ui.westComp = null;
} }
ui.tabPane.doLayout(); ui.tabPane.doLayout();
} else if (DarkTabbedPaneUI.KEY_CENTER_TABS.endsWith(key)) {
ui.tabPane.doLayout();
ui.tabPane.repaint();
} }
} }

18
core/src/main/java/com/github/weisj/darklaf/ui/tabbedpane/DarkTabbedPaneLayout.java

@ -35,6 +35,24 @@ public class DarkTabbedPaneLayout extends TabbedPaneLayout {
this.ui = ui; this.ui = ui;
} }
@Override
protected void centerTabs(final int tabPlacement, final int tabCount, final int returnAt) {
if (ui.runCount == 1 && Boolean.TRUE.equals(ui.tabPane.getClientProperty(DarkTabbedPaneUI.KEY_CENTER_TABS))) {
if (ui.isHorizontalTabPlacement()) {
int shift = (returnAt - (ui.rects[tabCount - 1].x + ui.rects[tabCount - 1].width)) / 2;
for (int i = 0; i < tabCount; i++) {
ui.rects[i].x += shift;
}
} else {
int shift = (returnAt - (ui.rects[tabCount - 1].y + ui.rects[tabCount - 1].height)) / 2;
for (int i = 0; i < tabCount; i++) {
ui.rects[i].y += shift;
}
}
}
}
/* /*
* Non scroll-layout * Non scroll-layout
*/ */

27
core/src/main/java/com/github/weisj/darklaf/ui/tabbedpane/DarkTabbedPaneScrollLayout.java

@ -325,6 +325,12 @@ public class DarkTabbedPaneScrollLayout extends TabbedPaneScrollLayout {
shiftBoundsToVisibleX(selectedBounds, leftMargin, returnAt, tabCount); shiftBoundsToVisibleX(selectedBounds, leftMargin, returnAt, tabCount);
} }
restoreHiddenTabsX(leftMargin, returnAt, tabCount); restoreHiddenTabsX(leftMargin, returnAt, tabCount);
if (ui.minVisible == 0 && ui.maxVisible == tabCount - 1
&& Boolean.TRUE.equals(ui.tabPane.getClientProperty(DarkTabbedPaneUI.KEY_CENTER_TABS))) {
adjustForCenterX(leftMargin, returnAt, tabCount);
}
if (tabsButton.isVisible() && ui.tabPane.getSelectedIndex() < ui.maxVisible) { if (tabsButton.isVisible() && ui.tabPane.getSelectedIndex() < ui.maxVisible) {
//Shift again. Hiding the the tab button might reveal the last tab. //Shift again. Hiding the the tab button might reveal the last tab.
//Only do this if the last visible tab is not currently selected. //Only do this if the last visible tab is not currently selected.
@ -339,6 +345,7 @@ public class DarkTabbedPaneScrollLayout extends TabbedPaneScrollLayout {
adjustForDropX(leftMargin, returnAt, tabCount); adjustForDropX(leftMargin, returnAt, tabCount);
layoutMoreTabsButton(tabCount); layoutMoreTabsButton(tabCount);
commitShiftX(ui.currentShiftXTmp, tabCount); commitShiftX(ui.currentShiftXTmp, tabCount);
ui.currentShiftX = ui.currentShiftXTmp; ui.currentShiftX = ui.currentShiftXTmp;
@ -371,6 +378,12 @@ public class DarkTabbedPaneScrollLayout extends TabbedPaneScrollLayout {
shiftBoundsToVisibleY(selectedBounds, topMargin, returnAt, tabCount); shiftBoundsToVisibleY(selectedBounds, topMargin, returnAt, tabCount);
} }
restoreHiddenTabsY(topMargin, returnAt, tabCount); restoreHiddenTabsY(topMargin, returnAt, tabCount);
if (ui.minVisible == 0 && ui.maxVisible == tabCount - 1
&& Boolean.TRUE.equals(ui.tabPane.getClientProperty(DarkTabbedPaneUI.KEY_CENTER_TABS))) {
adjustForCenterY(topMargin, returnAt, tabCount);
}
if (tabsButton.isVisible() && ui.tabPane.getSelectedIndex() < ui.maxVisible) { if (tabsButton.isVisible() && ui.tabPane.getSelectedIndex() < ui.maxVisible) {
shiftTabsY(0, topMargin, bottomMargin, tabCount, false); shiftTabsY(0, topMargin, bottomMargin, tabCount, false);
if (ui.minVisible > 0 || ui.maxVisible < tabCount - 1) { if (ui.minVisible > 0 || ui.maxVisible < tabCount - 1) {
@ -390,6 +403,20 @@ public class DarkTabbedPaneScrollLayout extends TabbedPaneScrollLayout {
ui.tabScroller.tabPanel.setPreferredSize(tabBounds.getSize()); ui.tabScroller.tabPanel.setPreferredSize(tabBounds.getSize());
} }
@Override
protected void centerTabs(final int tabPlacement, final int tabCount, final int returnAt) {
// Do nothing.
}
protected void adjustForCenterX(final int leftMargin, final int returnAt, final int tabCount) {
int shift = (returnAt - (ui.rects[tabCount - 1].x + ui.rects[tabCount - 1].width)) / 2;
shiftTabsX(shift, 0, returnAt, tabCount - 1, true);
}
protected void adjustForCenterY(final int topMargin, final int returnAt, final int tabCount) {
int shift = (returnAt - (ui.rects[tabCount - 1].y + ui.rects[tabCount - 1].height)) / 2;
shiftTabsY(shift, 0, returnAt, tabCount - 1, true);
}
@Override @Override
protected int preferredTabAreaWidth(final int tabPlacement, final int height) { protected int preferredTabAreaWidth(final int tabPlacement, final int height) {

6
core/src/main/java/com/github/weisj/darklaf/ui/tabbedpane/DarkTabbedPaneUI.java

@ -46,6 +46,12 @@ import java.util.function.Consumer;
public class DarkTabbedPaneUI extends DarkTabbedPaneUIBridge { public class DarkTabbedPaneUI extends DarkTabbedPaneUIBridge {
protected static final String KEY_PREFIX = "JTabbedPane."; protected static final String KEY_PREFIX = "JTabbedPane.";
/*
* Centering tabs only applies if in
* - WRAP_TAB_LAYOUT there is only one tab run.
* - SCROLL_TAB_LAYOUT the viewport doesn't need to be scrolled.
*/
public static final String KEY_CENTER_TABS = KEY_PREFIX + "centerTabs";
public static final String KEY_DND = KEY_PREFIX + "dndEnabled"; public static final String KEY_DND = KEY_PREFIX + "dndEnabled";
public static final String KEY_NORTH_COMP = KEY_PREFIX + "northComponent"; public static final String KEY_NORTH_COMP = KEY_PREFIX + "northComponent";
public static final String KEY_WEST_COMP = KEY_PREFIX + "westComponent"; public static final String KEY_WEST_COMP = KEY_PREFIX + "westComponent";

5
core/src/main/java/com/github/weisj/darklaf/ui/tabbedpane/TabbedPaneLayout.java

@ -30,7 +30,7 @@ import java.awt.*;
* This class should be treated as a &quot;protected&quot; inner class. Instantiate it only within subclasses of * This class should be treated as a &quot;protected&quot; inner class. Instantiate it only within subclasses of
* BasicTabbedPaneUI. * BasicTabbedPaneUI.
*/ */
public class TabbedPaneLayout implements LayoutManager { public abstract class TabbedPaneLayout implements LayoutManager {
protected final DarkTabbedPaneUIBridge ui; protected final DarkTabbedPaneUIBridge ui;
@ -395,6 +395,7 @@ public class TabbedPaneLayout implements LayoutManager {
} }
} }
centerTabs(tabPlacement, tabCount, returnAt);
// Pad the selected tab so that it appears raised in front // Pad the selected tab so that it appears raised in front
padSelectedTab(tabPlacement, selectedIndex); padSelectedTab(tabPlacement, selectedIndex);
@ -409,6 +410,8 @@ public class TabbedPaneLayout implements LayoutManager {
} }
} }
protected abstract void centerTabs(final int tabPlacement, final int tabCount, int returnAt);
/** /**
* Normalizes the tab runs. * Normalizes the tab runs.
* *

101
core/src/main/java/com/github/weisj/darklaf/ui/tabbedpane/TabbedPaneScrollLayout.java

@ -23,9 +23,6 @@
*/ */
package com.github.weisj.darklaf.ui.tabbedpane; package com.github.weisj.darklaf.ui.tabbedpane;
import javax.swing.*;
import java.awt.*;
abstract class TabbedPaneScrollLayout extends TabbedPaneLayout { abstract class TabbedPaneScrollLayout extends TabbedPaneLayout {
@ -33,103 +30,7 @@ abstract class TabbedPaneScrollLayout extends TabbedPaneLayout {
super(ui); super(ui);
} }
protected void calculateTabRects(final int tabPlacement, final int tabCount) { protected abstract void calculateTabRects(final int tabPlacement, final int tabCount);
FontMetrics metrics = ui.getFontMetrics();
Dimension size = ui.tabPane.getSize();
Insets insets = ui.tabPane.getInsets();
Insets tabAreaInsets = ui.getTabAreaInsets(tabPlacement);
int fontHeight = metrics.getHeight();
int selectedIndex = ui.tabPane.getSelectedIndex();
int i;
boolean verticalTabRuns = (tabPlacement == SwingConstants.LEFT || tabPlacement == SwingConstants.RIGHT);
boolean leftToRight = ui.tabPane.getComponentOrientation().isLeftToRight();
int x = tabAreaInsets.left;
int y = tabAreaInsets.top;
int totalWidth = 0;
int totalHeight = 0;
//
// Calculate bounds within which a tab run must fit
//
switch (tabPlacement) {
case SwingConstants.LEFT:
case SwingConstants.RIGHT:
ui.maxTabWidth = ui.calculateMaxTabWidth(tabPlacement);
break;
case SwingConstants.BOTTOM:
case SwingConstants.TOP:
default:
ui.maxTabHeight = ui.calculateMaxTabHeight(tabPlacement);
}
ui.runCount = 0;
ui.selectedRun = -1;
if (tabCount == 0) {
return;
}
ui.selectedRun = 0;
ui.runCount = 1;
// Run through tabs and lay them out in a single run
Rectangle rect;
for (i = 0; i < tabCount; i++) {
rect = ui.rects[i];
if (!verticalTabRuns) {
// Tabs on TOP or BOTTOM....
if (i > 0) {
rect.x = ui.rects[i - 1].x + ui.rects[i - 1].width;
} else {
ui.tabRuns[0] = 0;
ui.maxTabWidth = 0;
totalHeight += ui.maxTabHeight;
rect.x = x;
}
rect.width = ui.calculateTabWidth(tabPlacement, i, metrics);
totalWidth = rect.x + rect.width;
ui.maxTabWidth = Math.max(ui.maxTabWidth, rect.width);
rect.y = y;
rect.height = ui.maxTabHeight/* - 2*/;
} else {
// Tabs on LEFT or RIGHT...
if (i > 0) {
rect.y = ui.rects[i - 1].y + ui.rects[i - 1].height;
} else {
ui.tabRuns[0] = 0;
ui.maxTabHeight = 0;
totalWidth = ui.maxTabWidth;
rect.y = y;
}
rect.height = ui.calculateTabHeight(tabPlacement, i, fontHeight);
totalHeight = rect.y + rect.height;
ui.maxTabHeight = Math.max(ui.maxTabHeight, rect.height);
rect.x = x;
rect.width = ui.maxTabWidth/* - 2*/;
}
}
if (ui.tabsOverlapBorder) {
// Pad the selected tab so that it appears raised in front
padSelectedTab(tabPlacement, selectedIndex);
}
// if right to left and tab placement on the top or
// the bottom, flip x positions and adjust by widths
if (!leftToRight && !verticalTabRuns) {
int rightMargin = size.width
- (insets.right + tabAreaInsets.right);
for (i = 0; i < tabCount; i++) {
ui.rects[i].x = rightMargin - ui.rects[i].x - ui.rects[i].width;
}
}
ui.tabScroller.tabPanel.setPreferredSize(new Dimension(totalWidth, totalHeight));
}
protected int preferredTabAreaWidth(final int tabPlacement, final int height) { protected int preferredTabAreaWidth(final int tabPlacement, final int height) {
return ui.calculateMaxTabWidth(tabPlacement); return ui.calculateMaxTabWidth(tabPlacement);

Loading…
Cancel
Save