mirror of
https://github.com/JFormDesigner/FlatLaf.git
synced 2025-12-06 14:00:55 +03:00
- support key prefixes for Linux desktop environments (issue #974)
- support custom key prefixes (issue #649) - support multi-prefixed keys - changed handling of prefixed keys
This commit is contained in:
23
CHANGELOG.md
23
CHANGELOG.md
@@ -31,6 +31,12 @@ FlatLaf Change Log
|
|||||||
- Updated to latest versions and fixed various issues.
|
- Updated to latest versions and fixed various issues.
|
||||||
- Support customizing through properties files. (issue #824)
|
- Support customizing through properties files. (issue #824)
|
||||||
- SwingX: Support `JXTipOfTheDay` component. (issue #980)
|
- SwingX: Support `JXTipOfTheDay` component. (issue #980)
|
||||||
|
- Support key prefixes for Linux desktop environments (e.g. `[gnome]`, `[kde]`
|
||||||
|
or `[xfce]`) in properties files. (issue #974)
|
||||||
|
- Support custom key prefixes (e.g. `[win10]` or `[test]`) in properties files.
|
||||||
|
(issue #649)
|
||||||
|
- Support multi-prefixed keys (e.g. `[dark][gnome]TitlePane.buttonBackground`).
|
||||||
|
The value is only used if all prefixes match current platform/theme.
|
||||||
|
|
||||||
#### Fixed bugs
|
#### Fixed bugs
|
||||||
|
|
||||||
@@ -66,6 +72,23 @@ FlatLaf Change Log
|
|||||||
`com.formdev.flatlaf.intellijthemes.materialthemeuilite` from `Flat<theme>`
|
`com.formdev.flatlaf.intellijthemes.materialthemeuilite` from `Flat<theme>`
|
||||||
to `FlatMT<theme>`.
|
to `FlatMT<theme>`.
|
||||||
- Removed `Gruvbox Dark Medium` and `Gruvbox Dark Soft` themes.
|
- Removed `Gruvbox Dark Medium` and `Gruvbox Dark Soft` themes.
|
||||||
|
- Prefixed keys in properties files (e.g. `[dark]Button.background` or
|
||||||
|
`[win]Button.arc`) are now handled earlier than before. In previous versions,
|
||||||
|
prefixed keys always had higher priority than unprefixed keys and did always
|
||||||
|
overwrite unprefixed keys. Now prefixed keys are handled in same order as
|
||||||
|
unprefixed keys, which means that if a key is prefixed and unprefixed (e.g.
|
||||||
|
`[win]Button.arc` and `Button.arc`), the one which is last specified in
|
||||||
|
properties file is used.\
|
||||||
|
Following worked in previous versions, but now `Button.arc` is always `6`:
|
||||||
|
~~~properties
|
||||||
|
[win]Button.arc = 12
|
||||||
|
Button.arc = 6
|
||||||
|
~~~
|
||||||
|
This works in new (and old) versions:
|
||||||
|
~~~properties
|
||||||
|
Button.arc = 6
|
||||||
|
[win]Button.arc = 12
|
||||||
|
~~~
|
||||||
|
|
||||||
|
|
||||||
## 3.5.4
|
## 3.5.4
|
||||||
|
|||||||
@@ -37,6 +37,7 @@ import java.util.ArrayList;
|
|||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
import java.util.Enumeration;
|
import java.util.Enumeration;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
|
import java.util.HashSet;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Locale;
|
import java.util.Locale;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
@@ -44,6 +45,7 @@ import java.util.MissingResourceException;
|
|||||||
import java.util.Properties;
|
import java.util.Properties;
|
||||||
import java.util.ResourceBundle;
|
import java.util.ResourceBundle;
|
||||||
import java.util.ServiceLoader;
|
import java.util.ServiceLoader;
|
||||||
|
import java.util.Set;
|
||||||
import java.util.function.Consumer;
|
import java.util.function.Consumer;
|
||||||
import java.util.function.Function;
|
import java.util.function.Function;
|
||||||
import java.util.function.IntUnaryOperator;
|
import java.util.function.IntUnaryOperator;
|
||||||
@@ -100,6 +102,8 @@ public abstract class FlatLaf
|
|||||||
private static Map<String, String> globalExtraDefaults;
|
private static Map<String, String> globalExtraDefaults;
|
||||||
private Map<String, String> extraDefaults;
|
private Map<String, String> extraDefaults;
|
||||||
private static Function<String, Color> systemColorGetter;
|
private static Function<String, Color> systemColorGetter;
|
||||||
|
private static Set<String> uiKeyPlatformPrefixes;
|
||||||
|
private static Set<String> uiKeySpecialPrefixes;
|
||||||
|
|
||||||
private String desktopPropertyName;
|
private String desktopPropertyName;
|
||||||
private String desktopPropertyName2;
|
private String desktopPropertyName2;
|
||||||
@@ -1122,6 +1126,92 @@ public abstract class FlatLaf
|
|||||||
FlatLaf.systemColorGetter = systemColorGetter;
|
FlatLaf.systemColorGetter = systemColorGetter;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns UI key prefix, used in FlatLaf properties files, for light or dark themes.
|
||||||
|
* Return value is either {@code [light]} or {@code [dark]}.
|
||||||
|
*
|
||||||
|
* @since 3.6
|
||||||
|
*/
|
||||||
|
public static String getUIKeyLightOrDarkPrefix( boolean dark ) {
|
||||||
|
return dark ? "[dark]" : "[light]";
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns set of UI key prefixes, used in FlatLaf properties files, for current platform.
|
||||||
|
* If UI keys in properties files start with a prefix (e.g. {@code [someprefix]Button.background}),
|
||||||
|
* then they are only used if that prefix is contained in this set
|
||||||
|
* (or is one of {@code [light]} or {@code [dark]} depending on current theme).
|
||||||
|
* <p>
|
||||||
|
* By default, the set contains one or more of following prefixes:
|
||||||
|
* <ul>
|
||||||
|
* <li>{@code [win]} on Windows
|
||||||
|
* <li>{@code [mac]} on macOS
|
||||||
|
* <li>{@code [linux]} on Linux
|
||||||
|
* <li>{@code [unknown]} on other platforms
|
||||||
|
* <li>{@code [gnome]} on Linux with GNOME desktop environment
|
||||||
|
* <li>{@code [kde]} on Linux with KDE desktop environment
|
||||||
|
* <li>on Linux, the value of the environment variable {@code XDG_CURRENT_DESKTOP},
|
||||||
|
* split at colons and converted to lower case (e.g. if value of {@code XDG_CURRENT_DESKTOP}
|
||||||
|
* is {@code ubuntu:GNOME}, then {@code [ubuntu]} and {@code [gnome]})
|
||||||
|
* </ul>
|
||||||
|
* <p>
|
||||||
|
* You can add own prefixes to the set.
|
||||||
|
* The prefixes must start with '[' and end with ']' characters, otherwise they will be ignored.
|
||||||
|
*
|
||||||
|
* @since 3.6
|
||||||
|
*/
|
||||||
|
public static Set<String> getUIKeyPlatformPrefixes() {
|
||||||
|
if( uiKeyPlatformPrefixes == null ) {
|
||||||
|
uiKeyPlatformPrefixes = new HashSet<>();
|
||||||
|
uiKeyPlatformPrefixes.add(
|
||||||
|
SystemInfo.isWindows ? "[win]" :
|
||||||
|
SystemInfo.isMacOS ? "[mac]" :
|
||||||
|
SystemInfo.isLinux ? "[linux]" : "[unknown]" );
|
||||||
|
|
||||||
|
// Linux
|
||||||
|
if( SystemInfo.isLinux ) {
|
||||||
|
if( SystemInfo.isGNOME )
|
||||||
|
uiKeyPlatformPrefixes.add( "[gnome]" );
|
||||||
|
else if( SystemInfo.isKDE )
|
||||||
|
uiKeyPlatformPrefixes.add( "[kde]" );
|
||||||
|
|
||||||
|
// add values from XDG_CURRENT_DESKTOP for other desktops
|
||||||
|
String desktop = System.getenv( "XDG_CURRENT_DESKTOP" );
|
||||||
|
if( desktop != null ) {
|
||||||
|
// XDG_CURRENT_DESKTOP is a colon-separated list of strings
|
||||||
|
// https://specifications.freedesktop.org/desktop-entry-spec/latest/recognized-keys.html#key-onlyshowin
|
||||||
|
// e.g. "ubuntu:GNOME" on Ubuntu 24.10 or "GNOME-Classic:GNOME" on CentOS 7
|
||||||
|
for( String desk : StringUtils.split( desktop.toLowerCase( Locale.ENGLISH ), ':', true, true ) )
|
||||||
|
uiKeyPlatformPrefixes.add( '[' + desk + ']' );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return uiKeyPlatformPrefixes;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns set of special UI key prefixes, used in FlatLaf properties files.
|
||||||
|
* Unlike other prefixes, properties with special prefixes are preserved.
|
||||||
|
* You can access them using `UIManager`. E.g. `UIManager.get( "[someSpecialPrefix]someKey" )`.
|
||||||
|
* <p>
|
||||||
|
* By default, the set contains following special prefixes:
|
||||||
|
* <ul>
|
||||||
|
* <li>{@code [style]}
|
||||||
|
* </ul>
|
||||||
|
* <p>
|
||||||
|
* You can add own prefixes to the set.
|
||||||
|
* The prefixes must start with '[' and end with ']' characters, otherwise they will be ignored.
|
||||||
|
*
|
||||||
|
* @since 3.6
|
||||||
|
*/
|
||||||
|
public static Set<String> getUIKeySpecialPrefixes() {
|
||||||
|
if( uiKeySpecialPrefixes == null ) {
|
||||||
|
uiKeySpecialPrefixes = new HashSet<>();
|
||||||
|
uiKeySpecialPrefixes.add( "[style]" );
|
||||||
|
}
|
||||||
|
return uiKeySpecialPrefixes;
|
||||||
|
}
|
||||||
|
|
||||||
private static void reSetLookAndFeel() {
|
private static void reSetLookAndFeel() {
|
||||||
EventQueue.invokeLater( () -> {
|
EventQueue.invokeLater( () -> {
|
||||||
LookAndFeel lookAndFeel = UIManager.getLookAndFeel();
|
LookAndFeel lookAndFeel = UIManager.getLookAndFeel();
|
||||||
|
|||||||
@@ -41,6 +41,7 @@ import java.util.Locale;
|
|||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.Map.Entry;
|
import java.util.Map.Entry;
|
||||||
import java.util.Properties;
|
import java.util.Properties;
|
||||||
|
import java.util.Set;
|
||||||
import java.util.function.Consumer;
|
import java.util.function.Consumer;
|
||||||
import java.util.function.Function;
|
import java.util.function.Function;
|
||||||
import javax.swing.Icon;
|
import javax.swing.Icon;
|
||||||
@@ -62,7 +63,6 @@ import com.formdev.flatlaf.util.HSLColor;
|
|||||||
import com.formdev.flatlaf.util.LoggingFacade;
|
import com.formdev.flatlaf.util.LoggingFacade;
|
||||||
import com.formdev.flatlaf.util.SoftCache;
|
import com.formdev.flatlaf.util.SoftCache;
|
||||||
import com.formdev.flatlaf.util.StringUtils;
|
import com.formdev.flatlaf.util.StringUtils;
|
||||||
import com.formdev.flatlaf.util.SystemInfo;
|
|
||||||
import com.formdev.flatlaf.util.UIScale;
|
import com.formdev.flatlaf.util.UIScale;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -105,6 +105,39 @@ class UIDefaultsLoader
|
|||||||
return lafClasses;
|
return lafClasses;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static Properties newUIProperties( boolean dark ) {
|
||||||
|
// UI key prefixes
|
||||||
|
String lightOrDarkPrefix = FlatLaf.getUIKeyLightOrDarkPrefix( dark );
|
||||||
|
Set<String> platformPrefixes = FlatLaf.getUIKeyPlatformPrefixes();
|
||||||
|
Set<String> specialPrefixes = FlatLaf.getUIKeySpecialPrefixes();
|
||||||
|
|
||||||
|
return new Properties() {
|
||||||
|
@Override
|
||||||
|
public synchronized Object put( Object k, Object value ) {
|
||||||
|
// process key prefixes (while loading properties files)
|
||||||
|
String key = (String) k;
|
||||||
|
while( key.startsWith( "[" ) ) {
|
||||||
|
int closeIndex = key.indexOf( ']' );
|
||||||
|
if( closeIndex < 0 )
|
||||||
|
return null; // ignore property with invalid prefix
|
||||||
|
|
||||||
|
String prefix = key.substring( 0, closeIndex + 1 );
|
||||||
|
|
||||||
|
if( specialPrefixes.contains( prefix ) )
|
||||||
|
break; // keep special prefix
|
||||||
|
|
||||||
|
if( !lightOrDarkPrefix.equals( prefix ) && !platformPrefixes.contains( prefix ) )
|
||||||
|
return null; // ignore property
|
||||||
|
|
||||||
|
// prefix is known and enabled --> remove prefix
|
||||||
|
key = key.substring( closeIndex + 1 );
|
||||||
|
}
|
||||||
|
|
||||||
|
return super.put( key, value );
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
static void loadDefaultsFromProperties( List<Class<?>> lafClasses, List<FlatDefaultsAddon> addons,
|
static void loadDefaultsFromProperties( List<Class<?>> lafClasses, List<FlatDefaultsAddon> addons,
|
||||||
Consumer<Properties> intellijThemesHook, Properties additionalDefaults, boolean dark, UIDefaults defaults )
|
Consumer<Properties> intellijThemesHook, Properties additionalDefaults, boolean dark, UIDefaults defaults )
|
||||||
{
|
{
|
||||||
@@ -113,8 +146,10 @@ class UIDefaultsLoader
|
|||||||
// which avoids that system color getter is invoked multiple times
|
// which avoids that system color getter is invoked multiple times
|
||||||
systemColorCache = (FlatLaf.getSystemColorGetter() != null) ? new HashMap<>() : null;
|
systemColorCache = (FlatLaf.getSystemColorGetter() != null) ? new HashMap<>() : null;
|
||||||
|
|
||||||
|
// all properties files will be loaded into this map
|
||||||
|
Properties properties = newUIProperties( dark );
|
||||||
|
|
||||||
// load core properties files
|
// load core properties files
|
||||||
Properties properties = new Properties();
|
|
||||||
for( Class<?> lafClass : lafClasses ) {
|
for( Class<?> lafClass : lafClasses ) {
|
||||||
String propertiesName = '/' + lafClass.getName().replace( '.', '/' ) + ".properties";
|
String propertiesName = '/' + lafClass.getName().replace( '.', '/' ) + ".properties";
|
||||||
try( InputStream in = lafClass.getResourceAsStream( propertiesName ) ) {
|
try( InputStream in = lafClass.getResourceAsStream( propertiesName ) ) {
|
||||||
@@ -201,41 +236,6 @@ class UIDefaultsLoader
|
|||||||
if( additionalDefaults != null )
|
if( additionalDefaults != null )
|
||||||
properties.putAll( additionalDefaults );
|
properties.putAll( additionalDefaults );
|
||||||
|
|
||||||
// collect all platform specific keys (but do not modify properties)
|
|
||||||
ArrayList<String> platformSpecificKeys = new ArrayList<>();
|
|
||||||
for( Object okey : properties.keySet() ) {
|
|
||||||
String key = (String) okey;
|
|
||||||
if( key.startsWith( "[" ) &&
|
|
||||||
(key.startsWith( "[win]" ) ||
|
|
||||||
key.startsWith( "[mac]" ) ||
|
|
||||||
key.startsWith( "[linux]" ) ||
|
|
||||||
key.startsWith( "[light]" ) ||
|
|
||||||
key.startsWith( "[dark]" )) )
|
|
||||||
platformSpecificKeys.add( key );
|
|
||||||
}
|
|
||||||
|
|
||||||
// remove platform specific properties and re-add only properties
|
|
||||||
// for current platform, but with platform prefix removed
|
|
||||||
if( !platformSpecificKeys.isEmpty() ) {
|
|
||||||
// handle light/dark specific properties
|
|
||||||
String lightOrDarkPrefix = dark ? "[dark]" : "[light]";
|
|
||||||
for( String key : platformSpecificKeys ) {
|
|
||||||
if( key.startsWith( lightOrDarkPrefix ) )
|
|
||||||
properties.put( key.substring( lightOrDarkPrefix.length() ), properties.remove( key ) );
|
|
||||||
}
|
|
||||||
|
|
||||||
// handle platform specific properties
|
|
||||||
String platformPrefix =
|
|
||||||
SystemInfo.isWindows ? "[win]" :
|
|
||||||
SystemInfo.isMacOS ? "[mac]" :
|
|
||||||
SystemInfo.isLinux ? "[linux]" : "[unknown]";
|
|
||||||
for( String key : platformSpecificKeys ) {
|
|
||||||
Object value = properties.remove( key );
|
|
||||||
if( key.startsWith( platformPrefix ) )
|
|
||||||
properties.put( key.substring( platformPrefix.length() ), value );
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// get (and remove) wildcard replacements, which override all other defaults that end with same suffix
|
// get (and remove) wildcard replacements, which override all other defaults that end with same suffix
|
||||||
HashMap<String, String> wildcards = new HashMap<>();
|
HashMap<String, String> wildcards = new HashMap<>();
|
||||||
Iterator<Entry<Object, Object>> it = properties.entrySet().iterator();
|
Iterator<Entry<Object, Object>> it = properties.entrySet().iterator();
|
||||||
|
|||||||
@@ -42,7 +42,6 @@ import com.formdev.flatlaf.FlatClientProperties;
|
|||||||
import com.formdev.flatlaf.FlatLaf;
|
import com.formdev.flatlaf.FlatLaf;
|
||||||
import com.formdev.flatlaf.util.HiDPIUtils;
|
import com.formdev.flatlaf.util.HiDPIUtils;
|
||||||
import com.formdev.flatlaf.util.StringUtils;
|
import com.formdev.flatlaf.util.StringUtils;
|
||||||
import com.formdev.flatlaf.util.SystemInfo;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Support for styling components in CSS syntax.
|
* Support for styling components in CSS syntax.
|
||||||
@@ -325,22 +324,24 @@ public class FlatStylingSupport
|
|||||||
return null;
|
return null;
|
||||||
|
|
||||||
Map<String, Object> oldValues = new HashMap<>();
|
Map<String, Object> oldValues = new HashMap<>();
|
||||||
|
outer:
|
||||||
for( Map.Entry<String, Object> e : style.entrySet() ) {
|
for( Map.Entry<String, Object> e : style.entrySet() ) {
|
||||||
String key = e.getKey();
|
String key = e.getKey();
|
||||||
Object newValue = e.getValue();
|
Object newValue = e.getValue();
|
||||||
|
|
||||||
// handle key prefix
|
// handle key prefix
|
||||||
if( key.startsWith( "[" ) ) {
|
while( key.startsWith( "[" ) ) {
|
||||||
if( (SystemInfo.isWindows && key.startsWith( "[win]" )) ||
|
int closeIndex = key.indexOf( ']' );
|
||||||
(SystemInfo.isMacOS && key.startsWith( "[mac]" )) ||
|
if( closeIndex < 0 )
|
||||||
(SystemInfo.isLinux && key.startsWith( "[linux]" )) ||
|
continue outer;
|
||||||
(key.startsWith( "[light]" ) && !FlatLaf.isLafDark()) ||
|
|
||||||
(key.startsWith( "[dark]" ) && FlatLaf.isLafDark()) )
|
String prefix = key.substring( 0, closeIndex + 1 );
|
||||||
{
|
String lightOrDarkPrefix = FlatLaf.getUIKeyLightOrDarkPrefix( FlatLaf.isLafDark() );
|
||||||
// prefix is known and enabled --> remove prefix
|
if( !lightOrDarkPrefix.equals( prefix ) && !FlatLaf.getUIKeyPlatformPrefixes().contains( prefix ) )
|
||||||
key = key.substring( key.indexOf( ']' ) + 1 );
|
continue outer;
|
||||||
} else
|
|
||||||
continue;
|
// prefix is known and enabled --> remove prefix
|
||||||
|
key = key.substring( closeIndex + 1 );
|
||||||
}
|
}
|
||||||
|
|
||||||
Object oldValue = applyProperty.apply( key, newValue );
|
Object oldValue = applyProperty.apply( key, newValue );
|
||||||
|
|||||||
@@ -31,6 +31,7 @@ public class SystemInfo
|
|||||||
public static final boolean isWindows;
|
public static final boolean isWindows;
|
||||||
public static final boolean isMacOS;
|
public static final boolean isMacOS;
|
||||||
public static final boolean isLinux;
|
public static final boolean isLinux;
|
||||||
|
/** @since 3.6 */ public static final boolean isUnknownOS;
|
||||||
|
|
||||||
// OS versions
|
// OS versions
|
||||||
public static final long osVersion;
|
public static final long osVersion;
|
||||||
@@ -59,6 +60,7 @@ public class SystemInfo
|
|||||||
public static final boolean isJetBrainsJVM_11_orLater;
|
public static final boolean isJetBrainsJVM_11_orLater;
|
||||||
|
|
||||||
// UI toolkits
|
// UI toolkits
|
||||||
|
/** @since 3.6 */ public static final boolean isGNOME;
|
||||||
public static final boolean isKDE;
|
public static final boolean isKDE;
|
||||||
|
|
||||||
// other
|
// other
|
||||||
@@ -75,6 +77,7 @@ public class SystemInfo
|
|||||||
isWindows = osName.startsWith( "windows" );
|
isWindows = osName.startsWith( "windows" );
|
||||||
isMacOS = osName.startsWith( "mac" );
|
isMacOS = osName.startsWith( "mac" );
|
||||||
isLinux = osName.startsWith( "linux" );
|
isLinux = osName.startsWith( "linux" );
|
||||||
|
isUnknownOS = !isWindows && !isMacOS && !isLinux;
|
||||||
|
|
||||||
// OS versions
|
// OS versions
|
||||||
osVersion = scanVersion( System.getProperty( "os.version" ) );
|
osVersion = scanVersion( System.getProperty( "os.version" ) );
|
||||||
@@ -104,7 +107,13 @@ public class SystemInfo
|
|||||||
isJetBrainsJVM_11_orLater = isJetBrainsJVM && isJava_11_orLater;
|
isJetBrainsJVM_11_orLater = isJetBrainsJVM && isJava_11_orLater;
|
||||||
|
|
||||||
// UI toolkits
|
// UI toolkits
|
||||||
isKDE = (isLinux && System.getenv( "KDE_FULL_SESSION" ) != null);
|
String desktop = isLinux ? System.getenv( "XDG_CURRENT_DESKTOP" ) : null;
|
||||||
|
isGNOME = (isLinux &&
|
||||||
|
(System.getenv( "GNOME_DESKTOP_SESSION_ID" ) != null ||
|
||||||
|
(desktop != null && desktop.contains( "GNOME" ))));
|
||||||
|
isKDE = (isLinux &&
|
||||||
|
(System.getenv( "KDE_FULL_SESSION" ) != null ||
|
||||||
|
(desktop != null && desktop.contains( "KDE" ))));
|
||||||
|
|
||||||
// other
|
// other
|
||||||
isProjector = Boolean.getBoolean( "org.jetbrains.projector.server.enable" );
|
isProjector = Boolean.getBoolean( "org.jetbrains.projector.server.enable" );
|
||||||
|
|||||||
@@ -50,6 +50,9 @@ mini.font = -3
|
|||||||
#defaultFont = ...
|
#defaultFont = ...
|
||||||
|
|
||||||
# font weights
|
# font weights
|
||||||
|
# fallback for unknown platform
|
||||||
|
light.font = +0
|
||||||
|
semibold.font = +0
|
||||||
# Windows
|
# Windows
|
||||||
[win]light.font = "Segoe UI Light"
|
[win]light.font = "Segoe UI Light"
|
||||||
[win]semibold.font = "Segoe UI Semibold"
|
[win]semibold.font = "Segoe UI Semibold"
|
||||||
@@ -59,15 +62,12 @@ mini.font = -3
|
|||||||
# Linux
|
# Linux
|
||||||
[linux]light.font = "Lato Light", "Ubuntu Light", "Cantarell Light"
|
[linux]light.font = "Lato Light", "Ubuntu Light", "Cantarell Light"
|
||||||
[linux]semibold.font = "Lato Semibold", "Ubuntu Medium", "Montserrat SemiBold"
|
[linux]semibold.font = "Lato Semibold", "Ubuntu Medium", "Montserrat SemiBold"
|
||||||
# fallback for unknown platform
|
|
||||||
light.font = +0
|
|
||||||
semibold.font = +0
|
|
||||||
|
|
||||||
# monospaced
|
# monospaced
|
||||||
|
monospaced.font = Monospaced
|
||||||
[win]monospaced.font = Monospaced
|
[win]monospaced.font = Monospaced
|
||||||
[mac]monospaced.font = Menlo, Monospaced
|
[mac]monospaced.font = Menlo, Monospaced
|
||||||
[linux]monospaced.font = "Liberation Mono", "Ubuntu Mono", Monospaced
|
[linux]monospaced.font = "Liberation Mono", "Ubuntu Mono", Monospaced
|
||||||
monospaced.font = Monospaced
|
|
||||||
|
|
||||||
# styles
|
# styles
|
||||||
[style].h00 = font: $h00.font
|
[style].h00 = font: $h00.font
|
||||||
|
|||||||
@@ -95,8 +95,8 @@ Spinner.buttonDisabledArrowColor = $ComboBox.buttonDisabledArrowColor
|
|||||||
#---- TabbedPane ----
|
#---- TabbedPane ----
|
||||||
|
|
||||||
# colors from JBUI.CurrentTheme.DefaultTabs.inactiveUnderlineColor()
|
# colors from JBUI.CurrentTheme.DefaultTabs.inactiveUnderlineColor()
|
||||||
[light]TabbedPane.inactiveUnderlineColor = #9ca7b8
|
{*-light}TabbedPane.inactiveUnderlineColor = #9ca7b8
|
||||||
[dark]TabbedPane.inactiveUnderlineColor = #747a80
|
{*-dark}TabbedPane.inactiveUnderlineColor = #747a80
|
||||||
|
|
||||||
|
|
||||||
#---- ToggleButton ----
|
#---- ToggleButton ----
|
||||||
|
|||||||
@@ -17,6 +17,7 @@
|
|||||||
package com.formdev.flatlaf;
|
package com.formdev.flatlaf;
|
||||||
|
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
|
import java.util.Properties;
|
||||||
import java.util.function.Function;
|
import java.util.function.Function;
|
||||||
import com.formdev.flatlaf.UIDefaultsLoader.ValueType;
|
import com.formdev.flatlaf.UIDefaultsLoader.ValueType;
|
||||||
|
|
||||||
@@ -72,4 +73,8 @@ public class UIDefaultsLoaderAccessor
|
|||||||
{
|
{
|
||||||
return UIDefaultsLoader.parseColorRGBA( value );
|
return UIDefaultsLoader.parseColorRGBA( value );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static Properties newUIProperties( boolean dark ) {
|
||||||
|
return UIDefaultsLoader.newUIProperties( dark );
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -41,6 +41,7 @@ import org.fife.ui.autocomplete.ParameterChoicesProvider;
|
|||||||
import org.fife.ui.autocomplete.ParameterizedCompletion;
|
import org.fife.ui.autocomplete.ParameterizedCompletion;
|
||||||
import org.fife.ui.autocomplete.ParameterizedCompletion.Parameter;
|
import org.fife.ui.autocomplete.ParameterizedCompletion.Parameter;
|
||||||
import org.fife.ui.rsyntaxtextarea.RSyntaxTextArea;
|
import org.fife.ui.rsyntaxtextarea.RSyntaxTextArea;
|
||||||
|
import com.formdev.flatlaf.FlatLaf;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author Karl Tauber
|
* @author Karl Tauber
|
||||||
@@ -358,12 +359,18 @@ class FlatCompletionProvider
|
|||||||
lastKeys = keys;
|
lastKeys = keys;
|
||||||
|
|
||||||
completions.clear();
|
completions.clear();
|
||||||
|
outer:
|
||||||
for( String key : keys ) {
|
for( String key : keys ) {
|
||||||
if( key.startsWith( "[" ) ) {
|
while( key.startsWith( "[" ) ) {
|
||||||
// remove prefix
|
// remove prefix
|
||||||
int closeIndex = key.indexOf( ']' );
|
int closeIndex = key.indexOf( ']' );
|
||||||
if( closeIndex < 0 )
|
if( closeIndex < 0 )
|
||||||
continue;
|
continue outer;
|
||||||
|
|
||||||
|
String prefix = key.substring( 0, closeIndex + 1 );
|
||||||
|
if( FlatLaf.getUIKeySpecialPrefixes().contains( prefix ) )
|
||||||
|
continue outer; // can not reference properties with special prefix
|
||||||
|
|
||||||
key = key.substring( closeIndex + 1 );
|
key = key.substring( closeIndex + 1 );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -76,14 +76,21 @@ class FlatThemePropertiesBaseManager
|
|||||||
|
|
||||||
definedCoreKeys = new HashSet<>();
|
definedCoreKeys = new HashSet<>();
|
||||||
for( Properties properties : coreThemes.values() ) {
|
for( Properties properties : coreThemes.values() ) {
|
||||||
|
outer:
|
||||||
for( Object k : properties.keySet() ) {
|
for( Object k : properties.keySet() ) {
|
||||||
String key = (String) k;
|
String key = (String) k;
|
||||||
if( key.startsWith( "*." ) || key.startsWith( "@" ) )
|
if( key.startsWith( "*." ) || key.startsWith( "@" ) )
|
||||||
continue;
|
continue;
|
||||||
if( key.startsWith( "[" ) ) {
|
|
||||||
|
while( key.startsWith( "[" ) ) {
|
||||||
int closeIndex = key.indexOf( ']' );
|
int closeIndex = key.indexOf( ']' );
|
||||||
if( closeIndex < 0 )
|
if( closeIndex < 0 )
|
||||||
continue;
|
continue outer;
|
||||||
|
|
||||||
|
String prefix = key.substring( 0, closeIndex + 1 );
|
||||||
|
if( FlatLaf.getUIKeySpecialPrefixes().contains( prefix ) )
|
||||||
|
break; // keep special prefix
|
||||||
|
|
||||||
key = key.substring( closeIndex + 1 );
|
key = key.substring( closeIndex + 1 );
|
||||||
}
|
}
|
||||||
definedCoreKeys.add( key );
|
definedCoreKeys.add( key );
|
||||||
|
|||||||
@@ -33,7 +33,6 @@ import javax.swing.event.DocumentListener;
|
|||||||
import javax.swing.plaf.basic.BasicLookAndFeel;
|
import javax.swing.plaf.basic.BasicLookAndFeel;
|
||||||
import javax.swing.text.BadLocationException;
|
import javax.swing.text.BadLocationException;
|
||||||
import com.formdev.flatlaf.UIDefaultsLoaderAccessor;
|
import com.formdev.flatlaf.UIDefaultsLoaderAccessor;
|
||||||
import com.formdev.flatlaf.util.SystemInfo;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Supports parsing content of text area in FlatLaf properties syntax.
|
* Supports parsing content of text area in FlatLaf properties syntax.
|
||||||
@@ -54,17 +53,13 @@ class FlatThemePropertiesSupport
|
|||||||
private final Map<String, Object> parsedValueCache2 = new HashMap<>();
|
private final Map<String, Object> parsedValueCache2 = new HashMap<>();
|
||||||
private Set<String> allKeysCache;
|
private Set<String> allKeysCache;
|
||||||
private String baseTheme;
|
private String baseTheme;
|
||||||
|
private boolean lastDark;
|
||||||
|
|
||||||
private static long globalCacheInvalidationCounter;
|
private static long globalCacheInvalidationCounter;
|
||||||
private long cacheInvalidationCounter;
|
private long cacheInvalidationCounter;
|
||||||
|
|
||||||
private static Set<String> wildcardKeys;
|
private static Set<String> wildcardKeys;
|
||||||
|
|
||||||
private static final String platformPrefix =
|
|
||||||
SystemInfo.isWindows ? "[win]" :
|
|
||||||
SystemInfo.isMacOS ? "[mac]" :
|
|
||||||
SystemInfo.isLinux ? "[linux]" : "[unknown]";
|
|
||||||
|
|
||||||
FlatThemePropertiesSupport( FlatSyntaxTextArea textArea ) {
|
FlatThemePropertiesSupport( FlatSyntaxTextArea textArea ) {
|
||||||
this.textArea = textArea;
|
this.textArea = textArea;
|
||||||
|
|
||||||
@@ -115,6 +110,7 @@ class FlatThemePropertiesSupport
|
|||||||
|
|
||||||
private KeyValue getKeyValueAtLine( int line ) {
|
private KeyValue getKeyValueAtLine( int line ) {
|
||||||
try {
|
try {
|
||||||
|
// get text at line
|
||||||
int startOffset = textArea.getLineStartOffset( line );
|
int startOffset = textArea.getLineStartOffset( line );
|
||||||
int endOffset = textArea.getLineEndOffset( line );
|
int endOffset = textArea.getLineEndOffset( line );
|
||||||
String text = textArea.getText( startOffset, endOffset - startOffset );
|
String text = textArea.getText( startOffset, endOffset - startOffset );
|
||||||
@@ -134,11 +130,13 @@ class FlatThemePropertiesSupport
|
|||||||
text = text.substring( sepIndex + 1 );
|
text = text.substring( sepIndex + 1 );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// parse line
|
||||||
Properties properties = new Properties();
|
Properties properties = new Properties();
|
||||||
properties.load( new StringReader( text ) );
|
properties.load( new StringReader( text ) );
|
||||||
if( properties.isEmpty() )
|
if( properties.isEmpty() )
|
||||||
return null;
|
return null;
|
||||||
|
|
||||||
|
// get key and value for line
|
||||||
String key = (String) properties.keys().nextElement();
|
String key = (String) properties.keys().nextElement();
|
||||||
String value = properties.getProperty( key );
|
String value = properties.getProperty( key );
|
||||||
return new KeyValue( key, value );
|
return new KeyValue( key, value );
|
||||||
@@ -171,17 +169,7 @@ class FlatThemePropertiesSupport
|
|||||||
}
|
}
|
||||||
|
|
||||||
private String getPropertyOrWildcard( String key ) {
|
private String getPropertyOrWildcard( String key ) {
|
||||||
// get platform specific properties
|
String value = getProperty( key );
|
||||||
String value = getProperty( platformPrefix + key );
|
|
||||||
if( value != null )
|
|
||||||
return value;
|
|
||||||
|
|
||||||
// get light/dark specific properties
|
|
||||||
value = getProperty( (isDark( getBaseTheme() ) ? "[dark]" : "[light]") + key );
|
|
||||||
if( value != null )
|
|
||||||
return value;
|
|
||||||
|
|
||||||
value = getProperty( key );
|
|
||||||
if( value != null )
|
if( value != null )
|
||||||
return value;
|
return value;
|
||||||
|
|
||||||
@@ -213,9 +201,18 @@ class FlatThemePropertiesSupport
|
|||||||
if( propertiesCache != null )
|
if( propertiesCache != null )
|
||||||
return propertiesCache;
|
return propertiesCache;
|
||||||
|
|
||||||
propertiesCache = new Properties();
|
String text = textArea.getText();
|
||||||
try {
|
try {
|
||||||
propertiesCache.load( new StringReader( textArea.getText() ) );
|
propertiesCache = UIDefaultsLoaderAccessor.newUIProperties( lastDark );
|
||||||
|
propertiesCache.load( new StringReader( text ) );
|
||||||
|
|
||||||
|
// re-load if dark has changed (getBaseTheme() invokes getProperties()!!!)
|
||||||
|
boolean dark = isDark( getBaseTheme() );
|
||||||
|
if( lastDark != dark ) {
|
||||||
|
lastDark = dark;
|
||||||
|
propertiesCache = UIDefaultsLoaderAccessor.newUIProperties( lastDark );
|
||||||
|
propertiesCache.load( new StringReader( text ) );
|
||||||
|
}
|
||||||
} catch( IOException ex ) {
|
} catch( IOException ex ) {
|
||||||
ex.printStackTrace(); //TODO
|
ex.printStackTrace(); //TODO
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user