diff --git a/demos/theming-demo/src/main/java/org/pushingpixels/radiance/demo/theming/main/palette/ControlStates.java b/demos/theming-demo/src/main/java/org/pushingpixels/radiance/demo/theming/main/palette/ControlStates.java index f9fb9053b..1aab92399 100644 --- a/demos/theming-demo/src/main/java/org/pushingpixels/radiance/demo/theming/main/palette/ControlStates.java +++ b/demos/theming-demo/src/main/java/org/pushingpixels/radiance/demo/theming/main/palette/ControlStates.java @@ -43,7 +43,10 @@ import org.pushingpixels.radiance.theming.api.painter.fill.ClassicTonalFillPainter; import org.pushingpixels.radiance.theming.api.painter.fill.GlassTonalFillPainter; import org.pushingpixels.radiance.theming.api.painter.fill.SpecularRectangularFillPainter; -import org.pushingpixels.radiance.theming.api.palette.*; +import org.pushingpixels.radiance.theming.api.palette.ColorSchemeUtils; +import org.pushingpixels.radiance.theming.api.palette.RadianceColorScheme2; +import org.pushingpixels.radiance.theming.api.palette.SchemeResolverUtils; +import org.pushingpixels.radiance.theming.api.palette.TonalSkin; import org.pushingpixels.radiance.theming.api.shaper.ClassicButtonShaper; import org.pushingpixels.radiance.theming.internal.RadianceSynapse; @@ -108,8 +111,7 @@ public SampleSkin(RadianceColorScheme accentScheme) { ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFF20F490), /* isFidelity */ true, - /* isDark */ false, - /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver()), + /* isDark */ false), RadianceThemingSlices.ContainerColorTokensAssociationKind.MARK, ComponentState.getActiveStates()); @@ -117,8 +119,7 @@ public SampleSkin(RadianceColorScheme accentScheme) { ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFF20F490), /* isFidelity */ true, - /* isDark */ false, - /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver()), + /* isDark */ false), RadianceThemingSlices.ContainerColorTokensAssociationKind.HIGHLIGHT, ComponentState.getActiveStates()); diff --git a/demos/theming-demo/src/main/java/org/pushingpixels/radiance/demo/theming/main/palette/TonalCheck.java b/demos/theming-demo/src/main/java/org/pushingpixels/radiance/demo/theming/main/palette/TonalCheck.java index 057735d37..8438e52c6 100644 --- a/demos/theming-demo/src/main/java/org/pushingpixels/radiance/demo/theming/main/palette/TonalCheck.java +++ b/demos/theming-demo/src/main/java/org/pushingpixels/radiance/demo/theming/main/palette/TonalCheck.java @@ -32,7 +32,7 @@ import org.pushingpixels.radiance.demo.theming.main.Check; import org.pushingpixels.radiance.theming.api.RadianceSkin; import org.pushingpixels.radiance.theming.api.RadianceThemingCortex; -import org.pushingpixels.radiance.theming.api.skin.AutumnSkin; +import org.pushingpixels.radiance.theming.api.skin.MarinerSkin; import javax.swing.*; import java.awt.*; @@ -41,8 +41,7 @@ public class TonalCheck { public static void main(String[] args) { - RadianceSkin tonalSkin = new AutumnSkin.AutumnTonalSkin(); - //new ControlStates.SampleSkin(new AquaColorScheme()); + RadianceSkin tonalSkin = new MarinerSkin.MarinerTonalSkin(); RadianceThemingCortex.GlobalScope.registerWidget("org.pushingpixels.radiance.theming" + ".extras.api.tabbed.TabHoverPreviewWidget", JTabbedPane.class, false); diff --git a/theming-extras/src/main/java/org/pushingpixels/radiance/theming/extras/api/skinpack/OfficeSilver2007Skin.java b/theming-extras/src/main/java/org/pushingpixels/radiance/theming/extras/api/skinpack/OfficeSilver2007Skin.java index cd382398b..639e11aaf 100644 --- a/theming-extras/src/main/java/org/pushingpixels/radiance/theming/extras/api/skinpack/OfficeSilver2007Skin.java +++ b/theming-extras/src/main/java/org/pushingpixels/radiance/theming/extras/api/skinpack/OfficeSilver2007Skin.java @@ -287,28 +287,23 @@ public OfficeSilver2007TonalSkin() { ContainerColorTokens rolloverContainerTokens = ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFFFFD111), /* isFidelity */ true, - /* isDark */ false, - /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver()); + /* isDark */ false); ContainerColorTokens selectedContainerTokens = ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFFFFBD51), /* isFidelity */ true, - /* isDark */ false, - /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver()); + /* isDark */ false); ContainerColorTokens rolloverSelectedContainerTokens = ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFFFFA400), /* isFidelity */ true, - /* isDark */ false, - /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver()); + /* isDark */ false); ContainerColorTokens pressedContainerTokens = ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFFFF8C18), /* isFidelity */ true, - /* isDark */ false, - /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver()); + /* isDark */ false); ContainerColorTokens pressedSelectedContainerTokens = ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFFFF991C), /* isFidelity */ true, - /* isDark */ false, - /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver()); + /* isDark */ false); // register state-specific color schemes on rollovers, presses and selections officeSilverDefaultBundle.registerContainerTokens(rolloverContainerTokens, @@ -343,27 +338,32 @@ public OfficeSilver2007TonalSkin() { /* seed */ Hct.fromInt(0xFFFFD111), /* isFidelity */ true, /* isDark */ false, + /* contrastLevel */ 0.0, /* colorResolver */ activeMarksColorResolver); ContainerColorTokens selectedMarkContainerTokens = ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFFFFBD51), /* isFidelity */ true, /* isDark */ false, + /* contrastLevel */ 0.0, /* colorResolver */ activeMarksColorResolver); ContainerColorTokens rolloverSelectedMarkContainerTokens = ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFFFFA400), /* isFidelity */ true, /* isDark */ false, + /* contrastLevel */ 0.0, /* colorResolver */ activeMarksColorResolver); ContainerColorTokens pressedMarkContainerTokens = ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFFFF8C18), /* isFidelity */ true, /* isDark */ false, + /* contrastLevel */ 0.0, /* colorResolver */ activeMarksColorResolver); ContainerColorTokens pressedSelectedMarkContainerTokens = ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFFFF991C), /* isFidelity */ true, /* isDark */ false, + /* contrastLevel */ 0.0, /* colorResolver */ activeMarksColorResolver); // register state-specific color schemes on mark rollovers, presses and selections diff --git a/theming/src/main/java/org/pushingpixels/radiance/theming/api/painter/overlay/BottomShadowOverlayPainter.java b/theming/src/main/java/org/pushingpixels/radiance/theming/api/painter/overlay/BottomShadowOverlayPainter.java index 455020ec8..89e986334 100644 --- a/theming/src/main/java/org/pushingpixels/radiance/theming/api/painter/overlay/BottomShadowOverlayPainter.java +++ b/theming/src/main/java/org/pushingpixels/radiance/theming/api/painter/overlay/BottomShadowOverlayPainter.java @@ -29,8 +29,11 @@ */ package org.pushingpixels.radiance.theming.api.painter.overlay; -import org.pushingpixels.radiance.theming.api.RadianceThemingSlices; +import org.pushingpixels.radiance.theming.api.ComponentState; import org.pushingpixels.radiance.theming.api.RadianceSkin; +import org.pushingpixels.radiance.theming.api.RadianceThemingSlices; +import org.pushingpixels.radiance.theming.api.palette.TonalSkin; +import org.pushingpixels.radiance.theming.internal.utils.RadianceColorSchemeUtilities; import org.pushingpixels.radiance.theming.internal.utils.RadianceColorUtilities; import org.pushingpixels.radiance.theming.internal.utils.RadianceCoreUtilities; @@ -91,10 +94,15 @@ private BottomShadowOverlayPainter() { @Override public void paintOverlay(Graphics2D graphics, Component comp, - RadianceThemingSlices.DecorationAreaType decorationAreaType, int width, int height, - RadianceSkin skin) { - Color shadowColor = RadianceColorUtilities.deriveByBrightness( - RadianceColorUtilities.getBackgroundFillColor(comp), -0.4f); + RadianceThemingSlices.DecorationAreaType decorationAreaType, int width, int height, + RadianceSkin skin) { + + Color shadowColor = (skin instanceof TonalSkin) + ? RadianceColorSchemeUtilities.getContainerTokens(comp, + ComponentState.ENABLED, RadianceThemingSlices.ContainerType.NEUTRAL) + .getContainerOutline() + :RadianceColorUtilities.deriveByBrightness( + RadianceColorUtilities.getBackgroundFillColor(comp), -0.4f); Component topMostWithSameDecorationAreaType = RadianceCoreUtilities .getTopMostParentWithDecorationAreaType(comp, diff --git a/theming/src/main/java/org/pushingpixels/radiance/theming/api/painter/overlay/TopBezelTonalOverlayPainter.java b/theming/src/main/java/org/pushingpixels/radiance/theming/api/painter/overlay/TopBezelTonalOverlayPainter.java new file mode 100644 index 000000000..4753ded5a --- /dev/null +++ b/theming/src/main/java/org/pushingpixels/radiance/theming/api/painter/overlay/TopBezelTonalOverlayPainter.java @@ -0,0 +1,122 @@ +/* + * Copyright (c) 2005-2025 Radiance Kirill Grouchnikov. All Rights Reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * o Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * o Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * o Neither the name of the copyright holder nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, + * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR + * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, + * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; + * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, + * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, + * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ +package org.pushingpixels.radiance.theming.api.painter.overlay; + +import org.pushingpixels.radiance.common.api.RadianceCommonCortex; +import org.pushingpixels.radiance.theming.api.RadianceSkin; +import org.pushingpixels.radiance.theming.api.RadianceThemingSlices; +import org.pushingpixels.radiance.theming.api.colorscheme.ContainerColorTokensSingleColorQuery; +import org.pushingpixels.radiance.theming.api.palette.ExtendedContainerColorTokens; +import org.pushingpixels.radiance.theming.internal.utils.RadianceCoreUtilities; + +import javax.swing.*; +import java.awt.*; + +/** + * Overlay painter that paints a bezel line at the top edge of the relevant + * decoration area. This class is part of officially supported API. + * + * @author Kirill Grouchnikov + */ +public final class TopBezelTonalOverlayPainter implements RadianceOverlayPainter { + /** + * Used to compute the color of the top line painted by this overlay + * painter. + */ + ContainerColorTokensSingleColorQuery colorSchemeQueryTop; + + /** + * Used to compute the color of the bottom line painted by this overlay + * painter. + */ + ContainerColorTokensSingleColorQuery colorSchemeQueryBottom; + + /** + * Creates a new overlay painter that paints a bezel line at the top edge of + * the relevant decoration area + * + * @param colorSchemeQueryTop Used to compute the color of the top line painted by this + * overlay painter. + * @param colorSchemeQueryBottom Used to compute the color of the bottom line painted by this + * overlay painter. + */ + public TopBezelTonalOverlayPainter( + ContainerColorTokensSingleColorQuery colorSchemeQueryTop, + ContainerColorTokensSingleColorQuery colorSchemeQueryBottom) { + + this.colorSchemeQueryTop = colorSchemeQueryTop; + this.colorSchemeQueryBottom = colorSchemeQueryBottom; + } + + @Override + public void paintOverlay(Graphics2D g, Component comp, + RadianceThemingSlices.DecorationAreaType decorationAreaType, int width, int height, + RadianceSkin skin) { + Component topMostWithSameDecorationAreaType = RadianceCoreUtilities + .getTopMostParentWithDecorationAreaType(comp, + decorationAreaType); + + Point inTopMost = SwingUtilities.convertPoint(comp, new Point(0, 0), + topMostWithSameDecorationAreaType); + int dy = inTopMost.y; + + Graphics2D graphics = (Graphics2D) g.create(); + // Important - do not set KEY_STROKE_CONTROL to VALUE_STROKE_PURE, as that instructs AWT + // to not normalize coordinates to paint at full pixels, and will result in blurry + // outlines. + graphics.setRenderingHint(RenderingHints.KEY_ANTIALIASING, + RenderingHints.VALUE_ANTIALIAS_ON); + + RadianceCommonCortex.paintAtScale1x(graphics, 0, 0, width, height, + (graphics1X, x, y, scaledWidth, scaledHeight, scaleFactor) -> { + ExtendedContainerColorTokens surfaceTokens = + skin.getBackgroundExtendedContainerTokens(decorationAreaType); + + graphics1X.setColor(this.colorSchemeQueryTop.query( + surfaceTokens.getBaseContainerTokens())); + + int topY = -(int) (scaleFactor * dy); + graphics1X.drawLine(0, topY, scaledWidth, topY); + + graphics1X.setColor(this.colorSchemeQueryBottom.query( + surfaceTokens.getBaseContainerTokens())); + + int bezelY = 1 - (int) (scaleFactor * dy); + graphics1X.drawLine(0, bezelY, scaledWidth, bezelY); + }); + + graphics.dispose(); + } + + @Override + public String getDisplayName() { + return "Top Bezel"; + } +} diff --git a/theming/src/main/java/org/pushingpixels/radiance/theming/api/palette/ColorSchemeUtils.java b/theming/src/main/java/org/pushingpixels/radiance/theming/api/palette/ColorSchemeUtils.java index 86b42900f..577acf738 100644 --- a/theming/src/main/java/org/pushingpixels/radiance/theming/api/palette/ColorSchemeUtils.java +++ b/theming/src/main/java/org/pushingpixels/radiance/theming/api/palette/ColorSchemeUtils.java @@ -500,17 +500,26 @@ public ContainerColorTokens getSystemEmergencyContainerTokens() { }; } + public static ContainerColorTokens getContainerTokens( + Hct seed, + boolean isFidelity, + boolean isDark) { + return getContainerTokens(seed, isFidelity, isDark, 0.0, + PaletteResolverUtils.getPaletteTonalColorResolver()); + } + public static ContainerColorTokens getContainerTokens( Hct seed, boolean isFidelity, boolean isDark, + double contrastLevel, PaletteContainerColorsResolver colorResolver) { DynamicPalette dynamicPalette = new DynamicPalette( /* sourceColorHct */ seed, /* isFidelity */ isFidelity, /* isDark */ isDark, - /* contrastLevel */ 0.0, + /* contrastLevel */ contrastLevel, /* palette */ TonalPalette.fromHct(seed)); return new ContainerColorTokens() { @@ -581,20 +590,30 @@ public float getContainerOutlineDisabledAlpha() { }; } + public static ExtendedContainerColorTokens getExtendedContainerTokens( + Hct seed, + boolean isFidelity, + boolean isDark) { + return getExtendedContainerTokens(seed, isFidelity, isDark, 0.0, + PaletteResolverUtils.getPaletteTonalColorResolver()); + } + public static ExtendedContainerColorTokens getExtendedContainerTokens( Hct seed, boolean isFidelity, boolean isDark, + double contrastLevel, PaletteContainerColorsResolver colorResolver) { DynamicPalette dynamicPalette = new DynamicPalette( /* sourceColorHct */ seed, /* isFidelity */ isFidelity, /* isDark */ isDark, - /* contrastLevel */ 0.0, + /* contrastLevel */ contrastLevel, /* palette */ TonalPalette.fromHct(seed)); - ContainerColorTokens baseTokens = getContainerTokens(seed, isFidelity, isDark, colorResolver); + ContainerColorTokens baseTokens = getContainerTokens(seed, isFidelity, isDark, + contrastLevel, colorResolver); return new ExtendedContainerColorTokens() { @Override diff --git a/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/AutumnSkin.java b/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/AutumnSkin.java index 0cebf8e82..06521f280 100644 --- a/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/AutumnSkin.java +++ b/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/AutumnSkin.java @@ -208,6 +208,7 @@ public AutumnTonalSkin() { /* seed */ Hct.fromInt(0xFFFDBD72), /* isFidelity */ true, /* isDark */ false, + /* contrastLevel */ 0.0, /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver().overlayWith( PaletteContainerColorsResolverOverlay.builder() .onContainer(DynamicPalette::getTonalContainerOutline) @@ -226,6 +227,7 @@ public AutumnTonalSkin() { /* seed */ Hct.fromInt(0xFFFFCA8B), /* isFidelity */ true, /* isDark */ false, + /* contrastLevel */ 0.0, /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver().overlayWith( PaletteContainerColorsResolverOverlay.builder() .onContainer(DynamicPalette::getOnTonalContainerVariant) @@ -246,8 +248,7 @@ public AutumnTonalSkin() { ColorSchemeUtils.getExtendedContainerTokens( /* seed */ Hct.fromInt(0xFFFED8B2), /* isFidelity */ true, - /* isDark */ false, - /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver()), + /* isDark */ false), RadianceThemingSlices.DecorationAreaType.CONTROL_PANE); this.buttonShaper = new ClassicButtonShaper(); diff --git a/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/BusinessBlackSteelSkin.java b/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/BusinessBlackSteelSkin.java index 7f65b213c..fb7781259 100644 --- a/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/BusinessBlackSteelSkin.java +++ b/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/BusinessBlackSteelSkin.java @@ -33,7 +33,6 @@ import org.pushingpixels.radiance.theming.api.*; import org.pushingpixels.radiance.theming.api.colorscheme.RadianceColorScheme; import org.pushingpixels.radiance.theming.api.palette.ColorSchemeUtils; -import org.pushingpixels.radiance.theming.api.palette.PaletteResolverUtils; import org.pushingpixels.radiance.theming.api.palette.RadianceColorScheme2; import org.pushingpixels.radiance.theming.api.palette.SchemeResolverUtils; @@ -119,8 +118,7 @@ public BusinessBlackSteelTonalSkin() { .withWindowChromeHighlightsAccent(ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFF85A3B5), /* isFidelity */ true, - /* isDark */ false, - /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver())) + /* isDark */ false)) .withActiveControlsAccent(ColorSchemeUtils.getColorScheme( /* palettesSource */ new ColorSchemeUtils.FidelityPaletteSource( Hct.fromInt(0xFF98B7CC), Hct.fromInt(0xFFC4C8CC), Hct.fromInt(0xFFE4EAF0)), @@ -130,8 +128,7 @@ public BusinessBlackSteelTonalSkin() { .withHighlightsAccent(ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFFA1BCCF), /* isFidelity */ true, - /* isDark */ false, - /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver()))); + /* isDark */ false))); RadianceColorScheme2 controlPaneColorScheme = ColorSchemeUtils.getColorScheme( /* palettesSource */ new ColorSchemeUtils.FidelityPaletteSource( diff --git a/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/BusinessBlueSteelSkin.java b/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/BusinessBlueSteelSkin.java index 0067c46ad..342c11f99 100644 --- a/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/BusinessBlueSteelSkin.java +++ b/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/BusinessBlueSteelSkin.java @@ -33,7 +33,6 @@ import org.pushingpixels.radiance.theming.api.*; import org.pushingpixels.radiance.theming.api.colorscheme.RadianceColorScheme; import org.pushingpixels.radiance.theming.api.palette.ColorSchemeUtils; -import org.pushingpixels.radiance.theming.api.palette.PaletteResolverUtils; import org.pushingpixels.radiance.theming.api.palette.RadianceColorScheme2; import org.pushingpixels.radiance.theming.api.palette.SchemeResolverUtils; @@ -109,8 +108,7 @@ public BusinessBlueSteelTonalSkin() { .withWindowChromeHighlightsAccent(ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFF83AFCE), /* isFidelity */ true, - /* isDark */ false, - /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver())) + /* isDark */ false)) .withActiveControlsAccent(ColorSchemeUtils.getColorScheme( /* palettesSource */ new ColorSchemeUtils.FidelityPaletteSource( Hct.fromInt(0xFF98B7CC), Hct.fromInt(0xFFC4C8CC), Hct.fromInt(0xFFE4EAF0)), @@ -120,8 +118,7 @@ public BusinessBlueSteelTonalSkin() { .withHighlightsAccent(ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFFEBD296), /* isFidelity */ true, - /* isDark */ false, - /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver()))); + /* isDark */ false))); RadianceColorScheme2 controlPaneColorScheme = ColorSchemeUtils.getColorScheme( /* palettesSource */ new ColorSchemeUtils.FidelityPaletteSource( diff --git a/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/BusinessSkin.java b/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/BusinessSkin.java index 1214333fe..f3bf3e63c 100644 --- a/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/BusinessSkin.java +++ b/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/BusinessSkin.java @@ -31,7 +31,6 @@ import org.pushingpixels.ephemeral.chroma.hct.Hct; import org.pushingpixels.radiance.theming.api.palette.ColorSchemeUtils; -import org.pushingpixels.radiance.theming.api.palette.PaletteResolverUtils; import org.pushingpixels.radiance.theming.api.palette.SchemeResolverUtils; /** @@ -75,8 +74,7 @@ public BusinessTonalSkin() { .withWindowChromeHighlightsAccent(ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFFEBD296), /* isFidelity */ true, - /* isDark */ false, - /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver())) + /* isDark */ false)) .withActiveControlsAccent(ColorSchemeUtils.getColorScheme( /* palettesSource */ new ColorSchemeUtils.FidelityPaletteSource( Hct.fromInt(0xFFEAEDF3), Hct.fromInt(0xFFC4C8CC), Hct.fromInt(0xFFE5EAEF)), @@ -86,8 +84,7 @@ public BusinessTonalSkin() { .withHighlightsAccent(ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFFEBD296), /* isFidelity */ true, - /* isDark */ false, - /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver()))); + /* isDark */ false))); } @Override diff --git a/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/MarinerSkin.java b/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/MarinerSkin.java index 757426538..6c9a651e1 100644 --- a/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/MarinerSkin.java +++ b/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/MarinerSkin.java @@ -29,21 +29,24 @@ */ package org.pushingpixels.radiance.theming.api.skin; -import org.pushingpixels.radiance.theming.api.ComponentState; -import org.pushingpixels.radiance.theming.api.RadianceColorSchemeBundle; -import org.pushingpixels.radiance.theming.api.RadianceSkin; -import org.pushingpixels.radiance.theming.api.RadianceThemingSlices; +import org.pushingpixels.ephemeral.chroma.dynamiccolor.DynamicPalette; +import org.pushingpixels.ephemeral.chroma.hct.Hct; +import org.pushingpixels.radiance.theming.api.*; import org.pushingpixels.radiance.theming.api.colorscheme.ColorSchemeSingleColorQuery; import org.pushingpixels.radiance.theming.api.colorscheme.ColorTransform; +import org.pushingpixels.radiance.theming.api.colorscheme.ContainerColorTokensSingleColorQuery; import org.pushingpixels.radiance.theming.api.colorscheme.RadianceColorScheme; import org.pushingpixels.radiance.theming.api.painter.border.ClassicBorderPainter; +import org.pushingpixels.radiance.theming.api.painter.border.ClassicTonalBorderPainter; import org.pushingpixels.radiance.theming.api.painter.border.FractionBasedBorderPainter; +import org.pushingpixels.radiance.theming.api.painter.border.FractionBasedTonalBorderPainter; import org.pushingpixels.radiance.theming.api.painter.decoration.MatteDecorationPainter; import org.pushingpixels.radiance.theming.api.painter.fill.ClassicFillPainter; +import org.pushingpixels.radiance.theming.api.painter.fill.ClassicTonalFillPainter; import org.pushingpixels.radiance.theming.api.painter.fill.FractionBasedFillPainter; -import org.pushingpixels.radiance.theming.api.painter.overlay.BottomLineOverlayPainter; -import org.pushingpixels.radiance.theming.api.painter.overlay.BottomShadowOverlayPainter; -import org.pushingpixels.radiance.theming.api.painter.overlay.TopBezelOverlayPainter; +import org.pushingpixels.radiance.theming.api.painter.fill.FractionBasedTonalFillPainter; +import org.pushingpixels.radiance.theming.api.painter.overlay.*; +import org.pushingpixels.radiance.theming.api.palette.*; import org.pushingpixels.radiance.theming.api.shaper.ClassicButtonShaper; /** @@ -61,18 +64,18 @@ public class MarinerSkin extends RadianceSkin { * Overlay painter to paint a dark line along the bottom edge of the * menubar. */ - private BottomLineOverlayPainter menuOverlayPainter; + protected RadianceOverlayPainter menuOverlayPainter; /** * Overlay painter to paint a dark line along the bottom edge of the * toolbars. */ - private BottomLineOverlayPainter toolbarBottomLineOverlayPainter; + protected RadianceOverlayPainter toolbarBottomLineOverlayPainter; /** * Overlay painter to paint a bezel line along the top edge of the footer. */ - private TopBezelOverlayPainter footerTopBezelOverlayPainter; + protected RadianceOverlayPainter footerTopBezelOverlayPainter; /** * Creates a new Mariner skin. @@ -187,47 +190,183 @@ public MarinerSkin() { this.registerDecorationAreaSchemeBundle(footerSchemeBundle, footerBackgroundColorScheme, RadianceThemingSlices.DecorationAreaType.FOOTER, RadianceThemingSlices.DecorationAreaType.TOOLBAR, RadianceThemingSlices.DecorationAreaType.CONTROL_PANE); + this.configureOverlayPainters(); + + this.buttonShaper = new ClassicButtonShaper(); + this.fillPainter = new FractionBasedFillPainter("Mariner", new float[] {0.0f, 0.5f, 1.0f}, + new ColorSchemeSingleColorQuery[] {ColorSchemeSingleColorQuery.EXTRALIGHT, + ColorSchemeSingleColorQuery.LIGHT, ColorSchemeSingleColorQuery.MID}); + + this.decorationPainter = new MatteDecorationPainter(); + this.highlightFillPainter = new ClassicFillPainter(); + + this.borderPainter = new FractionBasedBorderPainter("Mariner", + new float[] {0.0f, 0.5f, 1.0f}, + new ColorSchemeSingleColorQuery[] {ColorSchemeSingleColorQuery.ULTRADARK, + ColorSchemeSingleColorQuery.DARK, ColorSchemeSingleColorQuery.MID}); + this.highlightBorderPainter = new ClassicBorderPainter(); + } + + void configureOverlayPainters() { // add an overlay painter to paint a bezel line along the top // edge of footer this.footerTopBezelOverlayPainter = new TopBezelOverlayPainter( - ColorSchemeSingleColorQuery.ULTRADARK, ColorSchemeSingleColorQuery.LIGHT); + ColorSchemeSingleColorQuery.ULTRADARK, ColorSchemeSingleColorQuery.LIGHT); this.addOverlayPainter(this.footerTopBezelOverlayPainter, RadianceThemingSlices.DecorationAreaType.FOOTER); - // add an overlay painters to create a line between + // add an overlay painter to create a line between // menu bar and toolbars this.menuOverlayPainter = new BottomLineOverlayPainter( - ColorSchemeSingleColorQuery.composite(ColorSchemeSingleColorQuery.ULTRADARK, - ColorTransform.brightness(-0.5f))); + ColorSchemeSingleColorQuery.composite(ColorSchemeSingleColorQuery.ULTRADARK, + ColorTransform.brightness(-0.5f))); this.addOverlayPainter(this.menuOverlayPainter, RadianceThemingSlices.DecorationAreaType.HEADER); // add overlay painter to paint drop shadows along the bottom // edges of toolbars this.addOverlayPainter(BottomShadowOverlayPainter.getInstance(100), - RadianceThemingSlices.DecorationAreaType.TOOLBAR); + RadianceThemingSlices.DecorationAreaType.TOOLBAR); // add overlay painter to paint a dark line along the bottom // edge of toolbars this.toolbarBottomLineOverlayPainter = new BottomLineOverlayPainter( - ColorSchemeSingleColorQuery.ULTRADARK); + ColorSchemeSingleColorQuery.ULTRADARK); this.addOverlayPainter(this.toolbarBottomLineOverlayPainter, RadianceThemingSlices.DecorationAreaType.TOOLBAR); - - this.buttonShaper = new ClassicButtonShaper(); - this.fillPainter = new FractionBasedFillPainter("Mariner", new float[] {0.0f, 0.5f, 1.0f}, - new ColorSchemeSingleColorQuery[] {ColorSchemeSingleColorQuery.EXTRALIGHT, - ColorSchemeSingleColorQuery.LIGHT, ColorSchemeSingleColorQuery.MID}); - - this.decorationPainter = new MatteDecorationPainter(); - this.highlightFillPainter = new ClassicFillPainter(); - - this.borderPainter = new FractionBasedBorderPainter("Mariner", - new float[] {0.0f, 0.5f, 1.0f}, - new ColorSchemeSingleColorQuery[] {ColorSchemeSingleColorQuery.ULTRADARK, - ColorSchemeSingleColorQuery.DARK, ColorSchemeSingleColorQuery.MID}); - this.highlightBorderPainter = new ClassicBorderPainter(); } @Override public String getDisplayName() { return NAME; } + + public static class MarinerTonalSkin extends MarinerSkin implements TonalSkin { + public static final String NAME = "Mariner Tonal"; + + public MarinerTonalSkin() { + RadianceColorScheme2 marinerColorScheme = ColorSchemeUtils.getColorScheme( + /* palettesSource */ new ColorSchemeUtils.FidelityPaletteSource( + Hct.fromInt(0xFFF6DD9D), Hct.fromInt(0xFFD9D8D5), Hct.fromInt(0xFFECF0F3)), + /* activeStatesContainerType */ ColorSchemeUtils.ActiveStatesContainerType.TONAL, + /* isDark */ false, + /* schemeColorResolver */ SchemeResolverUtils.getSchemeColorResolver()); + + ContainerColorTokens marinerSelectedContainerTokens = ColorSchemeUtils.getContainerTokens( + /* seed */ Hct.fromInt(0xFFF5D47A), + /* isFidelity */ true, + /* isDark */ false); + + RadianceColorSchemeBundle2 marinerDefaultBundle = + new RadianceColorSchemeBundle2(marinerColorScheme); + // More saturated seed for controls in selected state + marinerDefaultBundle.registerContainerTokens(marinerSelectedContainerTokens, + ComponentState.SELECTED); + this.registerDecorationAreaSchemeBundle(marinerDefaultBundle, + RadianceThemingSlices.DecorationAreaType.NONE); + + RadianceColorScheme2 marinerHeaderColorScheme = ColorSchemeUtils.getColorScheme( + /* palettesSource */ new ColorSchemeUtils.FidelityPaletteSource( + Hct.fromInt(0xFFF5D47A), Hct.fromInt(0xFF281D1E), Hct.fromInt(0xFF2C2021)), + /* activeStatesContainerType */ ColorSchemeUtils.ActiveStatesContainerType.TONAL, + /* isDark */ true, + /* schemeColorResolver */ SchemeResolverUtils.getSchemeColorResolver()); + + RadianceColorSchemeBundle2 marinerHeaderBundle = + new RadianceColorSchemeBundle2(marinerHeaderColorScheme); + // More saturated seed for controls in selected state + marinerHeaderBundle.registerContainerTokens(marinerSelectedContainerTokens, + ComponentState.SELECTED); + marinerHeaderBundle.registerContainerTokens( + marinerSelectedContainerTokens, + RadianceThemingSlices.ContainerColorTokensAssociationKind.HIGHLIGHT, + ComponentState.getActiveStates()); + this.registerDecorationAreaSchemeBundle(marinerHeaderBundle, + ColorSchemeUtils.getExtendedContainerTokens( + /* seed */ Hct.fromInt(0xFF261D1E), + /* isFidelity */ true, + /* isDark */ false, + /* contrastLevel */ 1.0, + /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver().overlayWith( + PaletteContainerColorsResolverOverlay.builder() + .containerOutline(DynamicPalette::getTonalContainerOutlineVariant) + .build())), + RadianceThemingSlices.DecorationAreaType.PRIMARY_TITLE_PANE, + RadianceThemingSlices.DecorationAreaType.SECONDARY_TITLE_PANE, + RadianceThemingSlices.DecorationAreaType.HEADER); + + RadianceColorScheme2 marinerFooterColorScheme = ColorSchemeUtils.getColorScheme( + /* palettesSource */ new ColorSchemeUtils.FidelityPaletteSource( + Hct.fromInt(0xFFF6DD9D), Hct.fromInt(0xFFC5C4C2), Hct.fromInt(0xFFB9B7B9)), + /* activeStatesContainerType */ ColorSchemeUtils.ActiveStatesContainerType.TONAL, + /* isDark */ false, + /* schemeColorResolver */ SchemeResolverUtils.getSchemeColorResolver()); + + RadianceColorSchemeBundle2 marinerFooterBundle = + new RadianceColorSchemeBundle2(marinerFooterColorScheme); + this.registerDecorationAreaSchemeBundle(marinerFooterBundle, + ColorSchemeUtils.getExtendedContainerTokens( + /* seed */ Hct.fromInt(0xFFB9B7B9), + /* isFidelity */ true, + /* isDark */ false), + RadianceThemingSlices.DecorationAreaType.FOOTER, + RadianceThemingSlices.DecorationAreaType.TOOLBAR, + RadianceThemingSlices.DecorationAreaType.CONTROL_PANE); + + this.buttonShaper = new ClassicButtonShaper(); + this.fillPainter = new FractionBasedTonalFillPainter("Mariner", new float[] {0.0f, 0.5f, 1.0f}, + new ContainerColorTokensSingleColorQuery[] { + ContainerColorTokensSingleColorQuery.CONTAINER_LOW, + ContainerColorTokensSingleColorQuery.CONTAINER, + ContainerColorTokensSingleColorQuery.CONTAINER_HIGH}); + + this.decorationPainter = new MatteDecorationPainter(); + this.highlightFillPainter = new ClassicTonalFillPainter(); + + this.borderPainter = new FractionBasedTonalBorderPainter("Mariner", + new float[] {0.0f, 1.0f}, + new ContainerColorTokensSingleColorQuery[] { + ContainerColorTokensSingleColorQuery.CONTAINER_OUTLINE, + ContainerColorTokensSingleColorQuery.CONTAINER_OUTLINE}); + this.highlightBorderPainter = new ClassicTonalBorderPainter(); + } + + @Override + void configureOverlayPainters() { + // add an overlay painter to paint a bezel line along the top + // edge of footer + this.footerTopBezelOverlayPainter = new TopBezelTonalOverlayPainter( + ContainerColorTokensSingleColorQuery.composite( + ContainerColorTokensSingleColorQuery.CONTAINER_OUTLINE, + ColorTransform.alpha(128)), + ContainerColorTokensSingleColorQuery.composite( + ContainerColorTokensSingleColorQuery.CONTAINER_OUTLINE_VARIANT, + ColorTransform.alpha(128))); + this.addOverlayPainter(this.footerTopBezelOverlayPainter, RadianceThemingSlices.DecorationAreaType.FOOTER); + + // add an overlay painter to create a line between + // menu bar and toolbars + this.menuOverlayPainter = new BottomLineTonalOverlayPainter( + ContainerColorTokensSingleColorQuery.composite( + ContainerColorTokensSingleColorQuery.CONTAINER_OUTLINE, + ColorTransform.brightness(-0.5f))); + this.addOverlayPainter(this.menuOverlayPainter, RadianceThemingSlices.DecorationAreaType.HEADER); + + // add overlay painter to paint drop shadows along the bottom + // edges of toolbars + this.addOverlayPainter(BottomShadowOverlayPainter.getInstance(50), + RadianceThemingSlices.DecorationAreaType.TOOLBAR); + + // add overlay painter to paint a dark line along the bottom + // edge of toolbars + this.toolbarBottomLineOverlayPainter = new BottomLineTonalOverlayPainter( + ContainerColorTokensSingleColorQuery.composite( + ContainerColorTokensSingleColorQuery.CONTAINER_OUTLINE, + ColorTransform.alpha(128))); + this.addOverlayPainter(this.toolbarBottomLineOverlayPainter, + RadianceThemingSlices.DecorationAreaType.TOOLBAR); + } + + @Override + public String getDisplayName() { + return MarinerTonalSkin.NAME; + } + } } diff --git a/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/ModerateSkin.java b/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/ModerateSkin.java index fc4caf9f9..0c8bb9e89 100644 --- a/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/ModerateSkin.java +++ b/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/ModerateSkin.java @@ -120,8 +120,7 @@ public ModerateTonalSkin() { ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFFF1D59A), /* isFidelity */ true, - /* isDark */ false, - /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver()); + /* isDark */ false); RadianceColorScheme2 steelBlueHeaderColorScheme = ColorSchemeUtils.getColorScheme( /* palettesSource */ new ColorSchemeUtils.FidelityPaletteSource( @@ -133,8 +132,7 @@ public ModerateTonalSkin() { ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFF6EA7CA), /* isFidelity */ true, - /* isDark */ false, - /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver()); + /* isDark */ false); RadianceColorScheme2 controlPaneColorScheme = ColorSchemeUtils.getColorScheme( /* palettesSource */ new ColorSchemeUtils.FidelityPaletteSource( diff --git a/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/RadianceMarinerLookAndFeel.java b/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/RadianceMarinerLookAndFeel.java index 30f86ce7b..5a91d4aa5 100644 --- a/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/RadianceMarinerLookAndFeel.java +++ b/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/RadianceMarinerLookAndFeel.java @@ -52,4 +52,10 @@ public class RadianceMarinerLookAndFeel extends RadianceLookAndFeel { public RadianceMarinerLookAndFeel() { super(new MarinerSkin()); } + + public static class RadianceMarinerTonalLookAndFeel extends RadianceLookAndFeel { + public RadianceMarinerTonalLookAndFeel() { + super(new MarinerSkin.MarinerTonalSkin()); + } + } } diff --git a/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/SaharaSkin.java b/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/SaharaSkin.java index 7d06b2db0..dffe2509f 100644 --- a/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/SaharaSkin.java +++ b/theming/src/main/java/org/pushingpixels/radiance/theming/api/skin/SaharaSkin.java @@ -113,8 +113,7 @@ public SaharaTonalSkin() { ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFFCAD0BE), /* isFidelity */ true, - /* isDark */ false, - /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver()); + /* isDark */ false); RadianceColorScheme2 desertHeaderColorScheme = ColorSchemeUtils.getColorScheme( /* palettesSource */ new ColorSchemeUtils.FidelityPaletteSource( @@ -126,8 +125,7 @@ public SaharaTonalSkin() { ColorSchemeUtils.getContainerTokens( /* seed */ Hct.fromInt(0xFFB2BC91), /* isFidelity */ true, - /* isDark */ false, - /* colorResolver */ PaletteResolverUtils.getPaletteTonalColorResolver()); + /* isDark */ false); RadianceColorSchemeBundle2 desertSandDefaultBundle = new RadianceColorSchemeBundle2(desertSandColorScheme); diff --git a/theming/src/main/java/org/pushingpixels/radiance/theming/internal/plugin/BaseSkinPlugin.java b/theming/src/main/java/org/pushingpixels/radiance/theming/internal/plugin/BaseSkinPlugin.java index 2eb3171f3..6ab57514a 100644 --- a/theming/src/main/java/org/pushingpixels/radiance/theming/internal/plugin/BaseSkinPlugin.java +++ b/theming/src/main/java/org/pushingpixels/radiance/theming/internal/plugin/BaseSkinPlugin.java @@ -126,6 +126,9 @@ public Set getSkins() { result.add(new SkinInfo(AutumnSkin.AutumnTonalSkin.NAME, AutumnSkin.AutumnTonalSkin.class::getName, RadianceAutumnLookAndFeel.RadianceAutumnTonalLookAndFeel.class::getName)); + result.add(new SkinInfo(MarinerSkin.MarinerTonalSkin.NAME, + MarinerSkin.MarinerTonalSkin.class::getName, + RadianceMarinerLookAndFeel.RadianceMarinerTonalLookAndFeel.class::getName)); return result; }