mirror of
https://github.com/NationalSecurityAgency/ghidra.git
synced 2026-09-28 17:11:11 -09:00
GP-2961 - Theme Fixes - Many changes to deal with odd rendering behavior in Nimbus and the Flat LaFs.
This commit is contained in:
@@ -8,6 +8,7 @@
|
||||
##MODULE IP: Tango Icons - Public Domain
|
||||
.classpath||GHIDRA||||END|
|
||||
Module.manifest||GHIDRA||||END|
|
||||
data/gui.laf.overrides.theme.properties||GHIDRA||||END|
|
||||
data/gui.palette.theme.properties||GHIDRA||||END|
|
||||
data/gui.theme.properties||GHIDRA||||END|
|
||||
src/main/java/ghidra/framework/options/package.html||GHIDRA||||END|
|
||||
|
||||
55
Ghidra/Framework/Gui/data/gui.laf.overrides.theme.properties
Normal file
55
Ghidra/Framework/Gui/data/gui.laf.overrides.theme.properties
Normal file
@@ -0,0 +1,55 @@
|
||||
[Defaults]
|
||||
|
||||
// TODO these are only here because they are used in the dark section; remove from here if done in
|
||||
// source code instead; otherwise, update error reporting to not require an entry in the default
|
||||
// section for values defined in specific LaF sections
|
||||
color.flat.text.original.bg = white // default 'text' value in Flat Light
|
||||
color.flat.selection.inactive.bg = #d3d3d3 // default value in Flat Light
|
||||
|
||||
|
||||
[Dark Defaults]
|
||||
|
||||
|
||||
|
||||
|
||||
[Flat Dark]
|
||||
|
||||
// the default inactive selection color is too close to the bg color to be easily visible
|
||||
color.flat.selection.inactive.bg = #0F4C6A
|
||||
|
||||
//
|
||||
// We would like widgets to use a bg color. By default widgets and some other items are all mapped
|
||||
// to 'text'. The easiest way to change all widgets is to change the value of 'text'. Then, for
|
||||
// any values that should still use the old value, we need to remap those. (The foreground colors
|
||||
// for these are mapped to 'textText'. For now, that value seems good enough that we do not need
|
||||
// to change it.)
|
||||
//
|
||||
color.flat.text.original.bg = #46494b // default 'text' value
|
||||
[color]text = color.bg
|
||||
[color]desktop = color.flat.text.original.bg
|
||||
[color]TableHeader = color.flat.text.original.bg
|
||||
[color]Checkbox.icon.background = color.flat.text.original.bg
|
||||
[color]Checkbox.icon.selectedBackground = color.flat.text.original.bg
|
||||
[color]CheckBox.icon[filled].checkmarkColor = color.flat.text.original.bg
|
||||
[color]ComboBox.buttonBackground = color.flat.text.original.bg
|
||||
[color]Spinner.background = color.flat.text.original.bg
|
||||
|
||||
|
||||
|
||||
[color]TextArea.background = color.bg
|
||||
[color]TextArea.foreground = color.fg
|
||||
|
||||
[color]TextPane.background = color.bg
|
||||
[color]TextPane.foreground = color.fg
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
[Nimbus]
|
||||
|
||||
// Nimbus uses the ToolTipPainter class to paint tooltips. That class does not read the property
|
||||
// we use for tooltips, which is 'ToolTip.background', even though that is defined by the LaF.
|
||||
// Setting the 'info' value here to changes the key the painter users to paint tooltips. The info
|
||||
// value seems to only be used for tooltips, which means this change affects no other components.
|
||||
[color]info = [color]ToolTip.background
|
||||
@@ -128,11 +128,6 @@ color.bg.tree = color.bg
|
||||
color.bg.tree.selected = [color]Tree.selectionBackground
|
||||
|
||||
|
||||
[Flat Dark]
|
||||
|
||||
// the default inactive selection color is too close to the bg color to be easily visible
|
||||
color.flat.selection.inactive = #0F4C6A
|
||||
|
||||
|
||||
[CDE/Motif]
|
||||
|
||||
@@ -140,10 +135,3 @@ color.bg = [color]window // gray for motif
|
||||
color.fg = [color]textText
|
||||
|
||||
|
||||
[Nimbus]
|
||||
|
||||
// Nimbus uses the ToolTipPainter class to paint tooltips. That class does not read the property
|
||||
// we use for tooltips, which is 'ToolTip.background', even though that is defined by the LaF.
|
||||
// Setting the 'info' value here to changes the key the painter users to paint tooltips. The info
|
||||
// value seems to only be used for tooltips, which means this change affects no other components.
|
||||
[color]info = [color]ToolTip.background
|
||||
|
||||
@@ -61,6 +61,11 @@ public class ColorValue extends ThemeValue<Color> {
|
||||
return outputId + " = " + getSerializedValue();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isExternal() {
|
||||
return !id.startsWith(COLOR_ID_PREFIX);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns true if the given key string is a valid external key for a color value
|
||||
* @param key the key string to test
|
||||
@@ -93,7 +98,7 @@ public class ColorValue extends ThemeValue<Color> {
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Color getUnresolvedReferenceValue(String id, String unresolvedId) {
|
||||
protected Color getUnresolvedReferenceValue(String primaryId, String unresolvedId) {
|
||||
|
||||
Throwable t = ReflectionUtilities.createThrowableWithStackOlderThan();
|
||||
StackTraceElement[] trace = t.getStackTrace();
|
||||
@@ -104,7 +109,7 @@ public class ColorValue extends ThemeValue<Color> {
|
||||
|
||||
Msg.error(this,
|
||||
"Could not resolve indirect color path for \"" + unresolvedId +
|
||||
"\" for primary id \"" + id + "\", using last resort default",
|
||||
"\" for primary id \"" + primaryId + "\", using last resort default",
|
||||
t);
|
||||
return LAST_RESORT_DEFAULT;
|
||||
}
|
||||
|
||||
@@ -57,6 +57,17 @@ public class FontValue extends ThemeValue<Font> {
|
||||
this.modifier = modifier;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getSerializationString() {
|
||||
String outputId = toExternalId(id);
|
||||
return outputId + " = " + getValueOutput();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isExternal() {
|
||||
return !id.startsWith(FONT_ID_PREFIX);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Font get(GThemeValueMap values) {
|
||||
Font font = super.get(values);
|
||||
@@ -66,12 +77,6 @@ public class FontValue extends ThemeValue<Font> {
|
||||
return font;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getSerializationString() {
|
||||
String outputId = toExternalId(id);
|
||||
return outputId + " = " + getValueOutput();
|
||||
}
|
||||
|
||||
private String getValueOutput() {
|
||||
if (referenceId != null) {
|
||||
String refId = toExternalId(referenceId);
|
||||
@@ -107,7 +112,7 @@ public class FontValue extends ThemeValue<Font> {
|
||||
* @param key the key to associate the parsed value with
|
||||
* @param value the font value to parse
|
||||
* @return a FontValue with the given key and the parsed value
|
||||
* @throws ParseException
|
||||
* @throws ParseException if there is an exception parsing
|
||||
*/
|
||||
public static FontValue parse(String key, String value) throws ParseException {
|
||||
String id = fromExternalId(key);
|
||||
@@ -148,10 +153,10 @@ public class FontValue extends ThemeValue<Font> {
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Font getUnresolvedReferenceValue(String id, String unresolvedId) {
|
||||
protected Font getUnresolvedReferenceValue(String primaryId, String unresolvedId) {
|
||||
Msg.warn(this,
|
||||
"Could not resolve indirect font path for \"" + unresolvedId +
|
||||
"\" for primary id \"" + id + "\", using last resort default");
|
||||
"\" for primary id \"" + primaryId + "\", using last resort default");
|
||||
return LAST_RESORT_DEFAULT;
|
||||
}
|
||||
|
||||
|
||||
@@ -74,6 +74,17 @@ public class IconValue extends ThemeValue<Icon> {
|
||||
this.modifier = modifier;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getSerializationString() {
|
||||
String outputId = toExternalId(id);
|
||||
return outputId + " = " + getValueOutput();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isExternal() {
|
||||
return !id.startsWith(ICON_ID_PREFIX);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Icon get(GThemeValueMap values) {
|
||||
Icon icon = super.get(values);
|
||||
@@ -83,12 +94,6 @@ public class IconValue extends ThemeValue<Icon> {
|
||||
return icon;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getSerializationString() {
|
||||
String outputId = toExternalId(id);
|
||||
return outputId + " = " + getValueOutput();
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns true if the given key string is a valid external key for an icon value
|
||||
* @param key the key string to test
|
||||
@@ -197,10 +202,10 @@ public class IconValue extends ThemeValue<Icon> {
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Icon getUnresolvedReferenceValue(String id, String unresolvedId) {
|
||||
protected Icon getUnresolvedReferenceValue(String primaryId, String unresolvedId) {
|
||||
Msg.warn(this,
|
||||
"Could not resolve indirect icon path for \"" + unresolvedId +
|
||||
"\" for primary id \"" + id + "\", using last resort default");
|
||||
"\" for primary id \"" + primaryId + "\", using last resort default");
|
||||
return LAST_RESORT_DEFAULT;
|
||||
}
|
||||
|
||||
|
||||
@@ -79,6 +79,7 @@ public class ThemePropertyFileReader extends AbstractThemeReader {
|
||||
return customSectionsMap;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void processNoSection(Section section) throws IOException {
|
||||
if (!section.isEmpty()) {
|
||||
error(section.getLineNumber(),
|
||||
@@ -125,17 +126,26 @@ public class ThemePropertyFileReader extends AbstractThemeReader {
|
||||
private void validate(String name, GThemeValueMap valuesMap) {
|
||||
for (String id : valuesMap.getColorIds()) {
|
||||
if (!defaults.containsColor(id)) {
|
||||
reportMissingDefaultsError("Color", name, id);
|
||||
ColorValue value = valuesMap.getColor(id);
|
||||
if (!value.isExternal()) {
|
||||
reportMissingDefaultsError("Color", name, id);
|
||||
}
|
||||
}
|
||||
}
|
||||
for (String id : valuesMap.getFontIds()) {
|
||||
if (!defaults.containsFont(id)) {
|
||||
reportMissingDefaultsError("Font", name, id);
|
||||
FontValue value = valuesMap.getFont(id);
|
||||
if (!value.isExternal()) {
|
||||
reportMissingDefaultsError("Font", name, id);
|
||||
}
|
||||
}
|
||||
}
|
||||
for (String id : valuesMap.getIconIds()) {
|
||||
if (!defaults.containsIcon(id)) {
|
||||
reportMissingDefaultsError("Icon", name, id);
|
||||
IconValue value = valuesMap.getIcon(id);
|
||||
if (!value.isExternal()) {
|
||||
reportMissingDefaultsError("Icon", name, id);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -41,6 +41,13 @@ public abstract class ThemeValue<T> implements Comparable<ThemeValue<T>> {
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
/**
|
||||
* True if this value is one that is one that is defined outside of the application, such as a
|
||||
* Java Look and Feel key.
|
||||
* @return true if external
|
||||
*/
|
||||
public abstract boolean isExternal();
|
||||
|
||||
/**
|
||||
* Returns the identifier for this ThemeValue.
|
||||
* @return the identifier for this ThemeValue.
|
||||
@@ -189,11 +196,11 @@ public abstract class ThemeValue<T> implements Comparable<ThemeValue<T>> {
|
||||
|
||||
/**
|
||||
* Returns the T to be used if the indirect reference couldn't be resolved.
|
||||
* @param id the id we are trying to get a value foe
|
||||
* @param primaryId the id we are trying to get a value for
|
||||
* @param unresolvedId the reference id that couldn't be resolved
|
||||
* @return the default value to be used if the indirect reference couldn't be resolved.
|
||||
*/
|
||||
protected abstract T getUnresolvedReferenceValue(String id, String unresolvedId);
|
||||
protected abstract T getUnresolvedReferenceValue(String primaryId, String unresolvedId);
|
||||
|
||||
/**
|
||||
* Returns the ThemeValue referred to by this ThemeValue. Needs to be overridden by
|
||||
|
||||
Reference in New Issue
Block a user