mirror of
https://github.com/JFormDesigner/FlatLaf.git
synced 2025-12-06 14:00:55 +03:00
Styling: Menu: support top-level underline selection
This commit is contained in:
@@ -18,6 +18,7 @@ package com.formdev.flatlaf.ui;
|
||||
|
||||
import java.awt.Color;
|
||||
import java.awt.Graphics;
|
||||
import java.awt.Insets;
|
||||
import java.awt.Window;
|
||||
import java.awt.event.ActionEvent;
|
||||
import java.beans.PropertyChangeListener;
|
||||
@@ -40,6 +41,7 @@ import javax.swing.plaf.UIResource;
|
||||
import javax.swing.plaf.basic.BasicMenuBarUI;
|
||||
import com.formdev.flatlaf.FlatClientProperties;
|
||||
import com.formdev.flatlaf.FlatLaf;
|
||||
import com.formdev.flatlaf.ui.FlatStylingSupport.Styleable;
|
||||
import com.formdev.flatlaf.ui.FlatStylingSupport.StyleableUI;
|
||||
import com.formdev.flatlaf.util.SystemInfo;
|
||||
|
||||
@@ -63,6 +65,15 @@ public class FlatMenuBarUI
|
||||
extends BasicMenuBarUI
|
||||
implements StyleableUI
|
||||
{
|
||||
// used in FlatMenuItemBorder
|
||||
/** @since 2 */ @Styleable protected Insets itemMargins;
|
||||
|
||||
// used in FlatMenuUI
|
||||
/** @since 2 */ @Styleable protected Color hoverBackground;
|
||||
/** @since 2 */ @Styleable protected Color underlineSelectionBackground;
|
||||
/** @since 2 */ @Styleable protected Color underlineSelectionColor;
|
||||
/** @since 2 */ @Styleable protected int underlineSelectionHeight = -1;
|
||||
|
||||
private PropertyChangeListener propertyChangeListener;
|
||||
private Map<String, Object> oldStyleValues;
|
||||
private AtomicBoolean borderShared;
|
||||
|
||||
@@ -18,9 +18,11 @@ package com.formdev.flatlaf.ui;
|
||||
|
||||
import static com.formdev.flatlaf.util.UIScale.scale;
|
||||
import java.awt.Component;
|
||||
import java.awt.Container;
|
||||
import java.awt.Insets;
|
||||
import javax.swing.JMenuBar;
|
||||
import javax.swing.UIManager;
|
||||
import javax.swing.plaf.MenuBarUI;
|
||||
|
||||
/**
|
||||
* Border for {@link javax.swing.JMenu}, {@link javax.swing.JMenuItem},
|
||||
@@ -33,15 +35,22 @@ import javax.swing.UIManager;
|
||||
public class FlatMenuItemBorder
|
||||
extends FlatMarginBorder
|
||||
{
|
||||
// only used if parent menubar is not a instance of FlatMenuBarUI
|
||||
private final Insets menuBarItemMargins = UIManager.getInsets( "MenuBar.itemMargins" );
|
||||
|
||||
@Override
|
||||
public Insets getBorderInsets( Component c, Insets insets ) {
|
||||
if( c.getParent() instanceof JMenuBar ) {
|
||||
insets.top = scale( menuBarItemMargins.top );
|
||||
insets.left = scale( menuBarItemMargins.left );
|
||||
insets.bottom = scale( menuBarItemMargins.bottom );
|
||||
insets.right = scale( menuBarItemMargins.right );
|
||||
Container parent = c.getParent();
|
||||
if( parent instanceof JMenuBar ) {
|
||||
// get margins from FlatMenuBarUI to allow styling
|
||||
MenuBarUI ui = ((JMenuBar)parent).getUI();
|
||||
Insets margins = (ui instanceof FlatMenuBarUI && ((FlatMenuBarUI)ui).itemMargins != null)
|
||||
? ((FlatMenuBarUI)ui).itemMargins
|
||||
: this.menuBarItemMargins;
|
||||
insets.top = scale( margins.top );
|
||||
insets.left = scale( margins.left );
|
||||
insets.bottom = scale( margins.bottom );
|
||||
insets.right = scale( margins.right );
|
||||
return insets;
|
||||
} else
|
||||
return super.getBorderInsets( c, insets );
|
||||
|
||||
@@ -23,15 +23,18 @@ import java.awt.Graphics;
|
||||
import java.awt.event.MouseEvent;
|
||||
import java.beans.PropertyChangeListener;
|
||||
import java.util.Map;
|
||||
import java.util.function.Function;
|
||||
import javax.swing.ButtonModel;
|
||||
import javax.swing.Icon;
|
||||
import javax.swing.JComponent;
|
||||
import javax.swing.JMenu;
|
||||
import javax.swing.JMenuBar;
|
||||
import javax.swing.JMenuItem;
|
||||
import javax.swing.LookAndFeel;
|
||||
import javax.swing.UIManager;
|
||||
import javax.swing.event.MouseInputListener;
|
||||
import javax.swing.plaf.ComponentUI;
|
||||
import javax.swing.plaf.MenuBarUI;
|
||||
import javax.swing.plaf.basic.BasicMenuUI;
|
||||
import com.formdev.flatlaf.ui.FlatStylingSupport.StyleableUI;
|
||||
import com.formdev.flatlaf.ui.FlatStylingSupport.UnknownStyleException;
|
||||
@@ -64,10 +67,10 @@ import com.formdev.flatlaf.ui.FlatStylingSupport.UnknownStyleException;
|
||||
* <!-- FlatMenuUI -->
|
||||
*
|
||||
* @uiDefault MenuItem.iconTextGap int
|
||||
* @uiDefault MenuBar.hoverBackground Color
|
||||
*
|
||||
* <!-- FlatMenuRenderer -->
|
||||
*
|
||||
* @uiDefault MenuBar.hoverBackground Color
|
||||
* @uiDefault MenuBar.underlineSelectionBackground Color
|
||||
* @uiDefault MenuBar.underlineSelectionColor Color
|
||||
* @uiDefault MenuBar.underlineSelectionHeight int
|
||||
@@ -78,7 +81,6 @@ public class FlatMenuUI
|
||||
extends BasicMenuUI
|
||||
implements StyleableUI
|
||||
{
|
||||
private Color hoverBackground;
|
||||
private FlatMenuItemRenderer renderer;
|
||||
private Map<String, Object> oldStyleValues;
|
||||
|
||||
@@ -101,7 +103,6 @@ public class FlatMenuUI
|
||||
|
||||
menuItem.setRolloverEnabled( true );
|
||||
|
||||
hoverBackground = UIManager.getColor( "MenuBar.hoverBackground" );
|
||||
renderer = createRenderer();
|
||||
}
|
||||
|
||||
@@ -109,7 +110,6 @@ public class FlatMenuUI
|
||||
protected void uninstallDefaults() {
|
||||
super.uninstallDefaults();
|
||||
|
||||
hoverBackground = null;
|
||||
renderer = null;
|
||||
oldStyleValues = null;
|
||||
}
|
||||
@@ -200,9 +200,10 @@ public class FlatMenuUI
|
||||
protected class FlatMenuRenderer
|
||||
extends FlatMenuItemRenderer
|
||||
{
|
||||
protected final Color menuBarUnderlineSelectionBackground = FlatUIUtils.getUIColor( "MenuBar.underlineSelectionBackground", underlineSelectionBackground );
|
||||
protected final Color menuBarUnderlineSelectionColor = FlatUIUtils.getUIColor( "MenuBar.underlineSelectionColor", underlineSelectionColor );
|
||||
protected final int menuBarUnderlineSelectionHeight = FlatUIUtils.getUIInt( "MenuBar.underlineSelectionHeight", underlineSelectionHeight );
|
||||
protected Color hoverBackground = UIManager.getColor( "MenuBar.hoverBackground" );
|
||||
protected Color menuBarUnderlineSelectionBackground = FlatUIUtils.getUIColor( "MenuBar.underlineSelectionBackground", underlineSelectionBackground );
|
||||
protected Color menuBarUnderlineSelectionColor = FlatUIUtils.getUIColor( "MenuBar.underlineSelectionColor", underlineSelectionColor );
|
||||
protected int menuBarUnderlineSelectionHeight = FlatUIUtils.getUIInt( "MenuBar.underlineSelectionHeight", underlineSelectionHeight );
|
||||
|
||||
protected FlatMenuRenderer( JMenuItem menuItem, Icon checkIcon, Icon arrowIcon,
|
||||
Font acceleratorFont, String acceleratorDelimiter )
|
||||
@@ -212,27 +213,39 @@ public class FlatMenuUI
|
||||
|
||||
@Override
|
||||
protected void paintBackground( Graphics g, Color selectionBackground ) {
|
||||
if( isUnderlineSelection() && ((JMenu)menuItem).isTopLevelMenu() )
|
||||
selectionBackground = menuBarUnderlineSelectionBackground;
|
||||
if( ((JMenu)menuItem).isTopLevelMenu() ) {
|
||||
if( isUnderlineSelection() )
|
||||
selectionBackground = getStyleFromMenuBarUI( ui -> ui.underlineSelectionBackground, menuBarUnderlineSelectionBackground );
|
||||
|
||||
ButtonModel model = menuItem.getModel();
|
||||
if( model.isRollover() && !model.isArmed() && !model.isSelected() &&
|
||||
model.isEnabled() && ((JMenu)menuItem).isTopLevelMenu() )
|
||||
{
|
||||
g.setColor( deriveBackground( hoverBackground ) );
|
||||
g.fillRect( 0, 0, menuItem.getWidth(), menuItem.getHeight() );
|
||||
} else
|
||||
super.paintBackground( g, selectionBackground );
|
||||
ButtonModel model = menuItem.getModel();
|
||||
if( model.isRollover() && !model.isArmed() && !model.isSelected() && model.isEnabled() ) {
|
||||
g.setColor( deriveBackground( getStyleFromMenuBarUI( ui -> ui.hoverBackground, hoverBackground ) ) );
|
||||
g.fillRect( 0, 0, menuItem.getWidth(), menuItem.getHeight() );
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
super.paintBackground( g, selectionBackground );
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void paintUnderlineSelection( Graphics g, Color underlineSelectionColor, int underlineSelectionHeight ) {
|
||||
if( ((JMenu)menuItem).isTopLevelMenu() ) {
|
||||
underlineSelectionColor = menuBarUnderlineSelectionColor;
|
||||
underlineSelectionHeight = menuBarUnderlineSelectionHeight;
|
||||
underlineSelectionColor = getStyleFromMenuBarUI( ui -> ui.underlineSelectionColor, menuBarUnderlineSelectionColor );
|
||||
underlineSelectionHeight = getStyleFromMenuBarUI( ui -> (ui.underlineSelectionHeight != -1)
|
||||
? ui.underlineSelectionHeight : null, menuBarUnderlineSelectionHeight );
|
||||
}
|
||||
|
||||
super.paintUnderlineSelection( g, underlineSelectionColor, underlineSelectionHeight );
|
||||
}
|
||||
|
||||
private <T> T getStyleFromMenuBarUI( Function<FlatMenuBarUI, T> f, T defaultValue ) {
|
||||
MenuBarUI ui = ((JMenuBar)menuItem.getParent()).getUI();
|
||||
if( !(ui instanceof FlatMenuBarUI) )
|
||||
return defaultValue;
|
||||
|
||||
T value = f.apply( (FlatMenuBarUI) ui );
|
||||
return (value != null) ? value : defaultValue;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -264,6 +264,12 @@ public class TestFlatStyleableInfo
|
||||
FlatMenuBarUI ui = (FlatMenuBarUI) c.getUI();
|
||||
|
||||
Map<String, Class<?>> expected = expectedMap(
|
||||
"itemMargins", Insets.class,
|
||||
"hoverBackground", Color.class,
|
||||
"underlineSelectionBackground", Color.class,
|
||||
"underlineSelectionColor", Color.class,
|
||||
"underlineSelectionHeight", int.class,
|
||||
|
||||
// FlatMenuBarBorder
|
||||
"borderColor", Color.class
|
||||
);
|
||||
|
||||
@@ -362,6 +362,12 @@ public class TestFlatStyling
|
||||
JMenuBar c = new JMenuBar();
|
||||
FlatMenuBarUI ui = (FlatMenuBarUI) c.getUI();
|
||||
|
||||
ui.applyStyle( "itemMargins: 1,2,3,4" );
|
||||
ui.applyStyle( "hoverBackground: #fff" );
|
||||
ui.applyStyle( "underlineSelectionBackground: #fff" );
|
||||
ui.applyStyle( "underlineSelectionColor: #fff" );
|
||||
ui.applyStyle( "underlineSelectionHeight: 3" );
|
||||
|
||||
// FlatMenuBarBorder
|
||||
ui.applyStyle( "borderColor: #fff" );
|
||||
|
||||
|
||||
Reference in New Issue
Block a user