From eb73afdc303556ef6b10223f61c089b49b4088cb Mon Sep 17 00:00:00 2001 From: weisj Date: Thu, 9 Apr 2020 22:27:17 +0200 Subject: [PATCH] Fixed window background not changing when theme is swapped on windows. Added borders for root pane. Allows for high contrast borders. --- .../components/border/MutableLineBorder.java | 36 ++++++++++++---- .../ui/rootpane/DarkRootPaneBorder.java | 43 +++++++++++++++++++ .../darklaf/ui/rootpane/DarkRootPaneUI.java | 24 +++++++++-- .../darklaf/properties/ui/rootPane.properties | 20 +++++---- .../high_contrast_dark_ui.properties | 1 + .../high_contrast_light_ui.properties | 1 + .../platform/windows/ui/WindowsTitlePane.java | 3 +- 7 files changed, 105 insertions(+), 23 deletions(-) create mode 100644 core/src/main/java/com/github/weisj/darklaf/ui/rootpane/DarkRootPaneBorder.java diff --git a/core/src/main/java/com/github/weisj/darklaf/components/border/MutableLineBorder.java b/core/src/main/java/com/github/weisj/darklaf/components/border/MutableLineBorder.java index 7816da43..774fd463 100644 --- a/core/src/main/java/com/github/weisj/darklaf/components/border/MutableLineBorder.java +++ b/core/src/main/java/com/github/weisj/darklaf/components/border/MutableLineBorder.java @@ -37,6 +37,9 @@ public class MutableLineBorder extends AbstractBorder { protected int right; protected int bottom; + public MutableLineBorder(final Insets insets, final Color color) { + this(insets.top, insets.left, insets.bottom, insets.right, color); + } public MutableLineBorder( final int top, final int left, final int bottom, final int right, final Color color) { @@ -51,10 +54,10 @@ public class MutableLineBorder extends AbstractBorder { public void paintBorder(final Component c, final Graphics g, final int x, final int y, final int width, final int height) { g.setColor(getColor()); - g.fillRect(x, y, width - right, top); - g.fillRect(x, y + top, left, height - top); - g.fillRect(x + left, y + height - bottom, width - left, bottom); - g.fillRect(x + width - right, y, right, height - bottom); + g.fillRect(x, y, width - getRight(), getTop()); + g.fillRect(x, y + getTop(), getLeft(), height - getTop()); + g.fillRect(x + getLeft(), y + height - getBottom(), width - getLeft(), getBottom()); + g.fillRect(x + width - getRight(), y, getRight(), height - getBottom()); } @Override @@ -79,17 +82,32 @@ public class MutableLineBorder extends AbstractBorder { @Override public Insets getBorderInsets(final Component c, final Insets insets) { - insets.left = left; - insets.top = top; - insets.right = right; - insets.bottom = bottom; + insets.left = getRight(); + insets.top = getTop(); + insets.right = getRight(); + insets.bottom = getBottom(); return insets; } public Insets getBorderInsets() { - return new Insets(top, left, bottom, right); + return getBorderInsets(null, new Insets(0, 0, 0, 0)); + } + + public int getTop() { + return top; + } + + public int getBottom() { + return bottom; + } + + public int getLeft() { + return left; } + public int getRight() { + return right; + } public void setTop(final int top) { this.top = top; diff --git a/core/src/main/java/com/github/weisj/darklaf/ui/rootpane/DarkRootPaneBorder.java b/core/src/main/java/com/github/weisj/darklaf/ui/rootpane/DarkRootPaneBorder.java new file mode 100644 index 00000000..8fcdbd14 --- /dev/null +++ b/core/src/main/java/com/github/weisj/darklaf/ui/rootpane/DarkRootPaneBorder.java @@ -0,0 +1,43 @@ +/* + * MIT License + * + * Copyright (c) 2020 Jannis Weis + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ +package com.github.weisj.darklaf.ui.rootpane; + +import com.github.weisj.darklaf.components.border.MutableLineBorder; +import com.github.weisj.darklaf.platform.DecorationsHandler; + +import javax.swing.*; +import javax.swing.plaf.UIResource; + +public class DarkRootPaneBorder extends MutableLineBorder implements UIResource { + + public DarkRootPaneBorder() { + super(UIManager.getInsets("RootPane.borderInsets"), UIManager.getColor("RootPane.borderColor")); + } + + @Override + public int getTop() { + return DecorationsHandler.getSharedInstance().isCustomDecorationSupported() + ? super.getTop() : 0; + } +} diff --git a/core/src/main/java/com/github/weisj/darklaf/ui/rootpane/DarkRootPaneUI.java b/core/src/main/java/com/github/weisj/darklaf/ui/rootpane/DarkRootPaneUI.java index 100d0f46..105430d5 100644 --- a/core/src/main/java/com/github/weisj/darklaf/ui/rootpane/DarkRootPaneUI.java +++ b/core/src/main/java/com/github/weisj/darklaf/ui/rootpane/DarkRootPaneUI.java @@ -49,6 +49,14 @@ public class DarkRootPaneUI extends BasicRootPaneUI implements HierarchyListener protected static final String KEY_PREFIX = "JRootPane."; public static final String KEY_NO_DECORATIONS_UPDATE = KEY_PREFIX + "noDecorationsUpdate"; public static final String KEY_NO_DECORATIONS = KEY_PREFIX + "noDecorations"; + protected static final String[] borderKeys = new String[]{ + "RootPane.border", "RootPane.frameBorder", "RootPane.plainDialogBorder", + "RootPane.informationDialogBorder", + "RootPane.errorDialogBorder", "RootPane.colorChooserDialogBorder", + "RootPane.fileChooserDialogBorder", "RootPane.questionDialogBorder", + "RootPane.warningDialogBorder" + }; + private Window window; private CustomTitlePane titlePane; private LayoutManager layoutManager; @@ -69,17 +77,28 @@ public class DarkRootPaneUI extends BasicRootPaneUI implements HierarchyListener super.installUI(c); rootPane = (JRootPane) c; windowDecorationsStyle = rootPane.getWindowDecorationStyle(); + LookAndFeel.installColors(rootPane, "RootPane.background", "RootPane.foreground"); updateClientDecoration(); + installBorder(rootPane); + } + + protected void installBorder(final JRootPane root) { + LookAndFeel.installBorder(root, borderKeys[windowDecorationsStyle]); } @Override public void uninstallUI(final JComponent c) { super.uninstallUI(c); uninstallClientDecorations(rootPane); + uninstallBorder(rootPane); layoutManager = null; rootPane = null; } + private static void uninstallBorder(final JRootPane root) { + LookAndFeel.uninstallBorder(root); + } + @Override public void propertyChange(final PropertyChangeEvent e) { super.propertyChange(e); @@ -89,6 +108,7 @@ public class DarkRootPaneUI extends BasicRootPaneUI implements HierarchyListener windowDecorationsStyle = decorationsStyleFromWindow(window, rootPane.getWindowDecorationStyle()); if (window instanceof JDialog) updateClientDecoration(); if (titlePane != null) titlePane.setDecorationsStyle(windowDecorationsStyle); + installBorder(rootPane); if (windowDecorationsStyle == JRootPane.PLAIN_DIALOG) { /* * Otherwise, the property change doesn't get fired when the dialog is a plain dialog. @@ -133,10 +153,6 @@ public class DarkRootPaneUI extends BasicRootPaneUI implements HierarchyListener window = null; } - private static void uninstallBorder(final JRootPane root) { - LookAndFeel.uninstallBorder(root); - } - private void uninstallLayout(final JRootPane root) { if (oldLayout != null) { root.setLayout(oldLayout); diff --git a/core/src/main/resources/com/github/weisj/darklaf/properties/ui/rootPane.properties b/core/src/main/resources/com/github/weisj/darklaf/properties/ui/rootPane.properties index d541380e..8f3d28a4 100644 --- a/core/src/main/resources/com/github/weisj/darklaf/properties/ui/rootPane.properties +++ b/core/src/main/resources/com/github/weisj/darklaf/properties/ui/rootPane.properties @@ -23,14 +23,16 @@ # SOFTWARE. # RootPaneUI = com.github.weisj.darklaf.ui.rootpane.DarkRootPaneUI -RootPane.background = %backgroundContainer -RootPane.frameBorder = null -RootPane.informationDialogBorder = null -RootPane.plainDialogBorder = null -RootPane.warningDialogBorder = null -RootPane.colorChooserDialogBorder = null -RootPane.fileChooserDialogBorder = null -RootPane.questionDialogBorder = null -RootPane.errorDialogBorder = null +RootPane.borderInsets = 0,0,0,0 +RootPane.borderColor = %border +RootPane.border = com.github.weisj.darklaf.ui.rootpane.DarkRootPaneBorder +RootPane.frameBorder = com.github.weisj.darklaf.ui.rootpane.DarkRootPaneBorder +RootPane.informationDialogBorder = com.github.weisj.darklaf.ui.rootpane.DarkRootPaneBorder +RootPane.plainDialogBorder = com.github.weisj.darklaf.ui.rootpane.DarkRootPaneBorder +RootPane.warningDialogBorder = com.github.weisj.darklaf.ui.rootpane.DarkRootPaneBorder +RootPane.colorChooserDialogBorder = com.github.weisj.darklaf.ui.rootpane.DarkRootPaneBorder +RootPane.fileChooserDialogBorder = com.github.weisj.darklaf.ui.rootpane.DarkRootPaneBorder +RootPane.questionDialogBorder = com.github.weisj.darklaf.ui.rootpane.DarkRootPaneBorder +RootPane.errorDialogBorder = com.github.weisj.darklaf.ui.rootpane.DarkRootPaneBorder diff --git a/theme/src/main/resources/com/github/weisj/darklaf/theme/high_contrast_dark/high_contrast_dark_ui.properties b/theme/src/main/resources/com/github/weisj/darklaf/theme/high_contrast_dark/high_contrast_dark_ui.properties index 7fe5b29d..e235a1a4 100644 --- a/theme/src/main/resources/com/github/weisj/darklaf/theme/high_contrast_dark/high_contrast_dark_ui.properties +++ b/theme/src/main/resources/com/github/weisj/darklaf/theme/high_contrast_dark/high_contrast_dark_ui.properties @@ -27,3 +27,4 @@ Button.borderless.drawOutline = true TabbedPane.selectedHoverBackground = %backgroundHover ToolTip.paintShadow = false ScrollBar.fadeEndColor = %ScrollBar.fadeStartColor +RootPane.borderInsets = 1,1,1,1 diff --git a/theme/src/main/resources/com/github/weisj/darklaf/theme/high_contrast_light/high_contrast_light_ui.properties b/theme/src/main/resources/com/github/weisj/darklaf/theme/high_contrast_light/high_contrast_light_ui.properties index a8b398aa..f1d9a508 100644 --- a/theme/src/main/resources/com/github/weisj/darklaf/theme/high_contrast_light/high_contrast_light_ui.properties +++ b/theme/src/main/resources/com/github/weisj/darklaf/theme/high_contrast_light/high_contrast_light_ui.properties @@ -30,3 +30,4 @@ TabbedPane.selectedHoverBackground = %backgroundHover TabFrameTab.selectedForeground = %textSelectionForeground TabFrameTab.hoverForeground = %textSelectionForeground ScrollBar.fadeEndColor = %ScrollBar.fadeStartColor +RootPane.borderInsets = 1,1,1,1 diff --git a/windows/src/main/java/com/github/weisj/darklaf/platform/windows/ui/WindowsTitlePane.java b/windows/src/main/java/com/github/weisj/darklaf/platform/windows/ui/WindowsTitlePane.java index 7879ba53..3629f033 100644 --- a/windows/src/main/java/com/github/weisj/darklaf/platform/windows/ui/WindowsTitlePane.java +++ b/windows/src/main/java/com/github/weisj/darklaf/platform/windows/ui/WindowsTitlePane.java @@ -228,7 +228,7 @@ public class WindowsTitlePane extends CustomTitlePane { if (windowHandle != 0) { JNIDecorationsWindows.installDecorations(windowHandle); updateResizeBehaviour(); - Color color = window.getBackground(); + Color color = rootPane.getBackground(); JNIDecorationsWindows.setBackground(windowHandle, color.getRed(), color.getGreen(), color.getBlue()); } else { uninstall(); @@ -794,6 +794,7 @@ public class WindowsTitlePane extends CustomTitlePane { repaint(); } else if (PropertyKey.BACKGROUND.equals(name) && pce.getNewValue() instanceof Color) { Color color = (Color) pce.getNewValue(); + System.out.println(color); if (color == null) return; JNIDecorationsWindows.setBackground(windowHandle, color.getRed(), color.getGreen(), color.getBlue()); }